huge wl fixup (wayland clients actually working again)
[platform/upstream/enlightenment.git] / src / bin / e_main.c
1 #include "e.h"
2
3 #define MAX_LEVEL 80
4
5 #define TS_DO
6 #ifdef TS_DO
7 # define TS(x)                                                    \
8   {                                                               \
9      t1 = ecore_time_unix_get();                                  \
10      printf("ESTART: %1.5f [%1.5f] - %s\n", t1 - t0, t1 - t2, x); \
11      t2 = t1;                                                     \
12   }
13 static double t0, t1, t2;
14 #else
15 # define TS(x)
16 #endif
17
18 /*
19  * i need to make more use of these when i'm baffled as to when something is
20  * up. other hooks:
21  *
22  *      void *(*__malloc_hook)(size_t size, const void *caller);
23  *
24  *      void *(*__realloc_hook)(void *ptr, size_t size, const void *caller);
25  *
26  *      void *(*__memalign_hook)(size_t alignment, size_t size,
27  *                               const void *caller);
28  *
29  *      void (*__free_hook)(void *ptr, const void *caller);
30  *
31  *      void (*__malloc_initialize_hook)(void);
32  *
33  *      void (*__after_morecore_hook)(void);
34  *
35
36    static void my_init_hook(void);
37    static void my_free_hook(void *p, const void *caller);
38
39    static void (*old_free_hook)(void *ptr, const void *caller) = NULL;
40    void (*__free_hook)(void *ptr, const void *caller);
41
42    void (*__malloc_initialize_hook) (void) = my_init_hook;
43    static void
44    my_init_hook(void)
45    {
46    old_free_hook = __free_hook;
47    __free_hook = my_free_hook;
48    }
49
50    //void *magicfree = NULL;
51
52    static void
53    my_free_hook(void *p, const void *caller)
54    {
55    __free_hook = old_free_hook;
56    //   if ((p) && (p == magicfree))
57    //     {
58    //   printf("CAUGHT!!!!! %p ...\n", p);
59    //   abort();
60    //     }
61    free(p);
62    __free_hook = my_free_hook;
63    }
64  */
65
66 /* local function prototypes */
67 static void      _e_main_shutdown(int errcode);
68 static void      _e_main_shutdown_push(int (*func)(void));
69 static void      _e_main_parse_arguments(int argc, char **argv);
70 static Eina_Bool _e_main_cb_signal_exit(void *data __UNUSED__, int ev_type __UNUSED__, void *ev __UNUSED__);
71 static Eina_Bool _e_main_cb_signal_hup(void *data __UNUSED__, int ev_type __UNUSED__, void *ev __UNUSED__);
72 static Eina_Bool _e_main_cb_signal_user(void *data __UNUSED__, int ev_type __UNUSED__, void *ev);
73 static int       _e_main_dirs_init(void);
74 static int       _e_main_dirs_shutdown(void);
75 static int       _e_main_path_init(void);
76 static int       _e_main_path_shutdown(void);
77 static void      _e_main_test_formats(void);
78 static int       _e_main_screens_init(void);
79 static int       _e_main_screens_shutdown(void);
80 static void      _e_main_desk_save(void);
81 static void      _e_main_desk_restore(void);
82 static void      _e_main_efreet_paths_init(void);
83 static void      _e_main_modules_load(Eina_Bool safe_mode);
84 static Eina_Bool _e_main_cb_x_flusher(void *data __UNUSED__);
85 static Eina_Bool _e_main_cb_idle_before(void *data __UNUSED__);
86 static Eina_Bool _e_main_cb_idle_after(void *data __UNUSED__);
87 static Eina_Bool _e_main_cb_startup_fake_end(void *data __UNUSED__);
88
89 /* local variables */
90 static Eina_Bool really_know = EINA_FALSE;
91 static Eina_Bool locked = EINA_FALSE;
92 static Eina_Bool inloop = EINA_FALSE;
93 static jmp_buf x_fatal_buff;
94
95 static int _e_main_lvl = 0;
96 static int(*_e_main_shutdown_func[MAX_LEVEL]) (void);
97
98 static Eina_List *_idle_before_list = NULL;
99 static Ecore_Idle_Enterer *_idle_before = NULL;
100 static Ecore_Idle_Enterer *_idle_after = NULL;
101 static Ecore_Idle_Enterer *_idle_flush = NULL;
102
103 static Ecore_Event_Handler *mod_init_end = NULL;
104
105 /* external variables */
106 EAPI Eina_Bool e_precache_end = EINA_FALSE;
107 EAPI Eina_Bool x_fatal = EINA_FALSE;
108 EAPI Eina_Bool good = EINA_FALSE;
109 EAPI Eina_Bool evil = EINA_FALSE;
110 EAPI Eina_Bool starting = EINA_TRUE;
111 EAPI Eina_Bool stopping = EINA_FALSE;
112 EAPI Eina_Bool restart = EINA_FALSE;
113 EAPI Eina_Bool e_nopause = EINA_FALSE;
114 EINTERN const char *e_first_frame = NULL;
115 EINTERN double e_first_frame_start_time = -1;
116
117 static void
118 _xdg_data_dirs_augment(void)
119 {
120    const char *s = getenv("XDG_DATA_DIRS");
121    const char *p = e_prefix_get();
122    char newpath[4096], buf[4096];
123
124    if (!p) return;
125
126    snprintf(newpath, sizeof(newpath), "%s:%s/share", e_prefix_data_get(), p);
127    if (s)
128      {
129         if (strncmp(s, newpath, strlen(newpath)))
130           {
131              snprintf(buf, sizeof(buf), "%s:%s", newpath, s);
132              e_util_env_set("XDG_DATA_DIRS", buf);
133           }
134      }
135    else
136      {
137         snprintf(buf, sizeof(buf), "%s:/usr/local/share:/usr/share", newpath);
138         e_util_env_set("XDG_DATA_DIRS", buf);
139      }
140
141    if (!getenv("XDG_RUNTIME_DIR"))
142      {
143         const char *dir;
144
145         snprintf(buf, sizeof(buf), "/tmp/xdg-XXXXXX");
146         dir = mkdtemp(buf);
147         if (!dir) dir = "/tmp";
148         e_util_env_set("XDG_RUNTIME_DIR", dir);
149      }
150 }
151
152 static Eina_Bool
153 _e_main_shelf_init_job(void *data EINA_UNUSED)
154 {
155    e_shelf_config_update();
156    return ECORE_CALLBACK_CANCEL;
157 }
158
159 /* externally accessible functions */
160 int
161 main(int argc, char **argv)
162 {
163    Eina_Bool nostartup = EINA_FALSE;
164    Eina_Bool safe_mode = EINA_FALSE;
165    Eina_Bool after_restart = EINA_FALSE;
166    Eina_Bool waslocked = EINA_FALSE;
167    double t = 0.0, tstart = 0.0;
168    char *s = NULL, buff[32];
169    struct sigaction action;
170 #ifdef TS_DO
171    t0 = t1 = t2 = ecore_time_unix_get();
172 #endif
173    TS("Begin Startup");
174
175    /* trap deadly bug signals and allow some form of sane recovery */
176    /* or ability to gdb attach and debug at this point - better than your */
177    /* wm/desktop vanishing and not knowing what happened */
178    if (!getenv("NOTIFY_SOCKET"))
179      {
180         TS("Signal Trap");
181         action.sa_sigaction = e_sigseg_act;
182         action.sa_flags = SA_NODEFER | SA_RESETHAND | SA_SIGINFO;
183         sigemptyset(&action.sa_mask);
184         sigaction(SIGSEGV, &action, NULL);
185
186         action.sa_sigaction = e_sigill_act;
187         action.sa_flags = SA_NODEFER | SA_RESETHAND | SA_SIGINFO;
188         sigemptyset(&action.sa_mask);
189         sigaction(SIGILL, &action, NULL);
190
191         action.sa_sigaction = e_sigfpe_act;
192         action.sa_flags = SA_NODEFER | SA_RESETHAND | SA_SIGINFO;
193         sigemptyset(&action.sa_mask);
194         sigaction(SIGFPE, &action, NULL);
195
196         action.sa_sigaction = e_sigbus_act;
197         action.sa_flags = SA_NODEFER | SA_RESETHAND | SA_SIGINFO;
198         sigemptyset(&action.sa_mask);
199         sigaction(SIGBUS, &action, NULL);
200
201         action.sa_sigaction = e_sigabrt_act;
202         action.sa_flags = SA_NODEFER | SA_RESETHAND | SA_SIGINFO;
203         sigemptyset(&action.sa_mask);
204         sigaction(SIGABRT, &action, NULL);
205         TS("Signal Trap Done");
206      }
207
208    t = ecore_time_unix_get();
209    s = getenv("E_START_TIME");
210    if ((s) && (!getenv("E_RESTART_OK")))
211      {
212         tstart = atof(s);
213         if ((t - tstart) < 5.0) safe_mode = EINA_TRUE;
214      }
215    tstart = t;
216    snprintf(buff, sizeof(buff), "%1.1f", tstart);
217    e_util_env_set("E_START_TIME", buff);
218
219    if (getenv("E_START_MTRACK"))
220      e_util_env_set("MTRACK", NULL);
221    TS("Eina Init");
222    if (!eina_init())
223      {
224         e_error_message_show(_("Enlightenment cannot initialize Eina!\n"));
225         _e_main_shutdown(-1);
226      }
227    _e_main_shutdown_push(eina_shutdown);
228    if (!e_log_init())
229      {
230         e_error_message_show(_("Enlightenment could not create a logging domain!\n"));
231         _e_main_shutdown(-1);
232      }
233 #ifdef TS_DO
234 #undef TS
235 # define TS(x)                                                    \
236   {                                                               \
237      t1 = ecore_time_unix_get();                                  \
238      printf("ESTART: %1.5f [%1.5f] - %s\n", t1 - t0, t1 - t2, x); \
239      t2 = t1;                                                     \
240   }
241 #endif
242    TS("Eina Init Done");
243    _e_main_shutdown_push(e_log_shutdown);
244
245    TS("Determine Prefix");
246    if (!e_prefix_determine(argv[0]))
247      {
248         fprintf(stderr,
249                 "ERROR: Enlightenment cannot determine it's installed\n"
250                 "       prefix from the system or argv[0].\n"
251                 "       This is because it is not on Linux AND has been\n"
252                 "       executed strangely. This is unusual.\n");
253      }
254    TS("Determine Prefix Done");
255
256    /* for debugging by redirecting stdout of e to a log file to tail */
257    setvbuf(stdout, NULL, _IONBF, 0);
258
259    TS("Environment Variables");
260    if (getenv("E_RESTART")) after_restart = EINA_TRUE;
261    if (getenv("DESKTOP_STARTUP_ID"))
262      e_util_env_set("DESKTOP_STARTUP_ID", NULL);
263    e_util_env_set("E_RESTART_OK", NULL);
264    e_util_env_set("PANTS", "ON");
265    e_util_env_set("DESKTOP", "Enlightenment-0.17.0");
266    TS("Environment Variables Done");
267
268    TS("Parse Arguments");
269    _e_main_parse_arguments(argc, argv);
270    TS("Parse Arguments Done");
271
272    /*** Initialize Core EFL Libraries We Need ***/
273
274    TS("Eet Init");
275    if (!eet_init())
276      {
277         e_error_message_show(_("Enlightenment cannot initialize Eet!\n"));
278         _e_main_shutdown(-1);
279      }
280    TS("Eet Init Done");
281    _e_main_shutdown_push(eet_shutdown);
282
283    TS("Ecore Init");
284    if (!ecore_init())
285      {
286         e_error_message_show(_("Enlightenment cannot initialize Ecore!\n"));
287         _e_main_shutdown(-1);
288      }
289    TS("Ecore Init Done");
290    _e_main_shutdown_push(ecore_shutdown);
291
292    e_first_frame = getenv("E_FIRST_FRAME");
293    if (e_first_frame && (!e_first_frame[0]))
294      e_first_frame = NULL;
295    else
296      e_first_frame_start_time = ecore_time_get();
297
298    TS("EIO Init");
299    if (!eio_init())
300      {
301         e_error_message_show(_("Enlightenment cannot initialize EIO!\n"));
302         _e_main_shutdown(-1);
303      }
304    TS("EIO Init Done");
305    _e_main_shutdown_push(eio_shutdown);
306
307    ecore_app_args_set(argc, (const char **)argv);
308
309    TS("Ecore Event Handlers");
310    if (!ecore_event_handler_add(ECORE_EVENT_SIGNAL_EXIT,
311                                 _e_main_cb_signal_exit, NULL))
312      {
313         e_error_message_show(_("Enlightenment cannot set up an exit signal handler.\n"
314                                "Perhaps you are out of memory?"));
315         _e_main_shutdown(-1);
316      }
317    if (!ecore_event_handler_add(ECORE_EVENT_SIGNAL_HUP,
318                                 _e_main_cb_signal_hup, NULL))
319      {
320         e_error_message_show(_("Enlightenment cannot set up a HUP signal handler.\n"
321                                "Perhaps you are out of memory?"));
322         _e_main_shutdown(-1);
323      }
324    if (!ecore_event_handler_add(ECORE_EVENT_SIGNAL_USER,
325                                 _e_main_cb_signal_user, NULL))
326      {
327         e_error_message_show(_("Enlightenment cannot set up a USER signal handler.\n"
328                                "Perhaps you are out of memory?"));
329         _e_main_shutdown(-1);
330      }
331    TS("Ecore Event Handlers Done");
332
333    TS("Ecore_File Init");
334    if (!ecore_file_init())
335      {
336         e_error_message_show(_("Enlightenment cannot initialize Ecore_File!\n"));
337         _e_main_shutdown(-1);
338      }
339    TS("Ecore_File Init Done");
340    _e_main_shutdown_push(ecore_file_shutdown);
341
342    TS("Ecore_Con Init");
343    if (!ecore_con_init())
344      {
345         e_error_message_show(_("Enlightenment cannot initialize Ecore_Con!\n"));
346         _e_main_shutdown(-1);
347      }
348    TS("Ecore_Con Init Done");
349    _e_main_shutdown_push(ecore_con_shutdown);
350
351    TS("Ecore_Ipc Init");
352    if (!ecore_ipc_init())
353      {
354         e_error_message_show(_("Enlightenment cannot initialize Ecore_Ipc!\n"));
355         _e_main_shutdown(-1);
356      }
357    TS("Ecore_Ipc Init Done");
358    _e_main_shutdown_push(ecore_ipc_shutdown);
359
360    _idle_before = ecore_idle_enterer_before_add(_e_main_cb_idle_before, NULL);
361
362    _xdg_data_dirs_augment();
363
364    TS("Ecore_Evas Init");
365    if (!ecore_evas_init())
366      {
367         e_error_message_show(_("Enlightenment cannot initialize Ecore_Evas!\n"));
368         _e_main_shutdown(-1);
369      }
370    TS("Ecore_Evas Init Done");
371 //   _e_main_shutdown_push(ecore_evas_shutdown);
372
373    TS("Elementary Init");
374    if (!elm_init(argc, argv))
375      {
376         e_error_message_show(_("Enlightenment cannot initialize Elementary!\n"));
377         _e_main_shutdown(-1);
378      }
379    TS("Elementary Init Done");
380    _e_main_shutdown_push(elm_shutdown);
381
382    TS("Emotion Init");
383    if (!emotion_init())
384      {
385         e_error_message_show(_("Enlightenment cannot initialize Emotion!\n"));
386         _e_main_shutdown(-1);
387      }
388    TS("Emotion Init Done");
389    _e_main_shutdown_push((void *)emotion_shutdown);
390
391    /* e doesn't sync to compositor - it should be one */
392    ecore_evas_app_comp_sync_set(0);
393
394    TS("Ecore_Evas Engine Check");
395    if (!ecore_evas_engine_type_supported_get(ECORE_EVAS_ENGINE_SOFTWARE_XCB))
396      {
397         if (!ecore_evas_engine_type_supported_get(ECORE_EVAS_ENGINE_SOFTWARE_XLIB))
398           {
399              e_error_message_show(_("Enlightenment found ecore_evas doesn't support the Software X11\n"
400                                     "rendering in Evas. Please check your installation of Evas and\n"
401                                     "Ecore and check they support the Software X11 rendering engine."));
402              _e_main_shutdown(-1);
403           }
404      }
405    if (!ecore_evas_engine_type_supported_get(ECORE_EVAS_ENGINE_SOFTWARE_BUFFER))
406      {
407         e_error_message_show(_("Enlightenment found ecore_evas doesn't support the Software Buffer\n"
408                                "rendering in Evas. Please check your installation of Evas and\n"
409                                "Ecore and check they support the Software Buffer rendering engine."));
410         _e_main_shutdown(-1);
411      }
412    TS("Ecore_Evas Engine Check Done");
413
414    TS("Edje Init");
415    if (!edje_init())
416      {
417         e_error_message_show(_("Enlightenment cannot initialize Edje!\n"));
418         _e_main_shutdown(-1);
419      }
420    TS("Edje Init Done");
421    _e_main_shutdown_push(edje_shutdown);
422    edje_freeze();
423
424    /*** Initialize E Subsystems We Need ***/
425
426    TS("E Intl Init");
427    if (!e_intl_init())
428      {
429         e_error_message_show(_("Enlightenment cannot initialize E_Intl!\n"));
430         _e_main_shutdown(-1);
431      }
432    TS("E Intl Init Done");
433    _e_main_shutdown_push(e_intl_shutdown);
434
435    /* init white box of death alert */
436    TS("E_Alert Init");
437    if (!e_alert_init())
438      {
439         e_error_message_show(_("Enlightenment cannot initialize its emergency alert system.\n"
440                                "Have you set your DISPLAY variable?"));
441         _e_main_shutdown(-1);
442      }
443    TS("E_Alert Init Done");
444    _e_main_shutdown_push(e_alert_shutdown);
445
446    TS("E_Configure Init");
447    e_configure_init();
448    TS("E_Configure Init Done");
449
450    TS("E Directories Init");
451    /* setup directories we will be using for configurations storage etc. */
452    if (!_e_main_dirs_init())
453      {
454         e_error_message_show(_("Enlightenment cannot create directories in your home directory.\n"
455                                "Perhaps you have no home directory or the disk is full?"));
456         _e_main_shutdown(-1);
457      }
458    TS("E Directories Init Done");
459    _e_main_shutdown_push(_e_main_dirs_shutdown);
460
461    TS("E_Filereg Init");
462    if (!e_filereg_init())
463      {
464         e_error_message_show(_("Enlightenment cannot set up its file registry system.\n"));
465         _e_main_shutdown(-1);
466      }
467    TS("E_Filereg Init Done");
468    _e_main_shutdown_push(e_filereg_shutdown);
469
470    TS("E_Config Init");
471    if (!e_config_init())
472      {
473         e_error_message_show(_("Enlightenment cannot set up its config system.\n"));
474         _e_main_shutdown(-1);
475      }
476    TS("E_Config Init Done");
477    _e_main_shutdown_push(e_config_shutdown);
478
479    TS("E_Env Init");
480    if (!e_env_init())
481      {
482         e_error_message_show(_("Enlightenment cannot set up its environment.\n"));
483         _e_main_shutdown(-1);
484      }
485    TS("E_Env Init Done");
486    _e_main_shutdown_push(e_env_shutdown);
487
488    e_util_env_set("E_ICON_THEME", e_config->icon_theme);
489    ecore_exe_run_priority_set(e_config->priority);
490    locked |= e_config->desklock_start_locked;
491
492    s = getenv("E_DESKLOCK_LOCKED");
493    if ((s) && (!strcmp(s, "locked"))) waslocked = EINA_TRUE;
494
495    TS("E_Pointer Init");
496    if (!e_pointer_init())
497      {
498         e_error_message_show(_("Enlightenment cannot set up its pointer system.\n"));
499         _e_main_shutdown(-1);
500      }
501    TS("E_Pointer Init Done");
502    _e_main_shutdown_push(e_pointer_shutdown);
503
504    TS("E Paths Init");
505    if (!_e_main_path_init())
506      {
507         e_error_message_show(_("Enlightenment cannot set up paths for finding files.\n"
508                                "Perhaps you are out of memory?"));
509         _e_main_shutdown(-1);
510      }
511    TS("E Paths Init Done");
512    _e_main_shutdown_push(_e_main_path_shutdown);
513
514    TS("E_Ipc Init");
515    if (!e_ipc_init()) _e_main_shutdown(-1);
516    TS("E_Ipc Init Done");
517    _e_main_shutdown_push(e_ipc_shutdown);
518
519    edje_frametime_set(1.0 / e_config->framerate);
520
521    TS("E_Font Init");
522    if (!e_font_init())
523      {
524         e_error_message_show(_("Enlightenment cannot set up its font system.\n"));
525         _e_main_shutdown(-1);
526      }
527    TS("E_Font Init Done");
528    _e_main_shutdown_push(e_font_shutdown);
529
530    TS("E_Font Apply");
531    e_font_apply();
532    TS("E_Font Apply Done");
533
534    TS("E_Canvas Recache");
535    e_canvas_recache();
536    TS("E_Canvas Recache Done");
537
538    TS("E_Theme Init");
539    if (!e_theme_init())
540      {
541         e_error_message_show(_("Enlightenment cannot set up its theme system.\n"));
542         _e_main_shutdown(-1);
543      }
544    TS("E_Theme Init Done");
545    _e_main_shutdown_push(e_theme_shutdown);
546
547    TS("E_Moveresize Init");
548    e_moveresize_init();
549    TS("E_Moveresize Init Done");
550    _e_main_shutdown_push(e_moveresize_shutdown);
551
552    if (e_config->show_splash)
553      e_init_status_set(_("Setup Message Bus"));
554    TS("E_Msgbus Init");
555    if (e_msgbus_init())
556      _e_main_shutdown_push(e_msgbus_shutdown);
557    TS("E_Msgbus Init Done");
558
559    TS("Efreet Init");
560    if (!efreet_init())
561      {
562         e_error_message_show(_("Enlightenment cannot initialize the FDO desktop system.\n"
563                                "Perhaps you lack permissions on ~/.cache/efreet or are\n"
564                                "out of memory or disk space?"));
565         _e_main_shutdown(-1);
566      }
567    TS("Efreet Init Done");
568    _e_main_shutdown_push(efreet_shutdown);
569
570    if (e_config->show_splash)
571      e_init_status_set(_("Starting International Support"));
572    TS("E_Intl Post Init");
573    if (!e_intl_post_init())
574      {
575         e_error_message_show(_("Enlightenment cannot set up its intl system.\n"));
576         _e_main_shutdown(-1);
577      }
578    TS("E_Intl Post Init Done");
579    _e_main_shutdown_push(e_intl_post_shutdown);
580
581    e_screensaver_preinit();
582
583    if (e_config->show_splash)
584      e_init_status_set(_("Setup Actions"));
585    TS("E_Actions Init");
586    if (!e_actions_init())
587      {
588         e_error_message_show(_("Enlightenment cannot set up its actions system.\n"));
589         _e_main_shutdown(-1);
590      }
591    TS("E_Actions Init Done");
592    _e_main_shutdown_push(e_actions_shutdown);
593
594    /* these just add event handlers and can't fail
595     * timestamping them is dumb.
596     */
597    e_zone_init();
598    e_desk_init();
599    e_menu_init();
600    e_exehist_init();
601
602
603    if (e_config->show_splash)
604      e_init_status_set(_("Setup Screensaver"));
605    TS("E_Screensaver Init");
606    if (!e_screensaver_init())
607      {
608         e_error_message_show(_("Enlightenment cannot configure the X screensaver.\n"));
609         _e_main_shutdown(-1);
610      }
611    TS("E_Screensaver Init Done");
612    _e_main_shutdown_push(e_screensaver_shutdown);
613
614    if (e_config->show_splash)
615      e_init_status_set(_("Setup Screens"));
616    TS("Screens Init");
617    if (!_e_main_screens_init())
618      {
619         e_error_message_show(_("Enlightenment set up window management for all the screens on your system\n"
620                                "failed. Perhaps another window manager is running?\n"));
621         _e_main_shutdown(-1);
622      }
623    TS("Screens Init Done");
624    _e_main_shutdown_push(_e_main_screens_shutdown);
625
626
627    TS("E_Scale Init");
628    if (!e_scale_init())
629      {
630         e_error_message_show(_("Enlightenment cannot set up its scale system.\n"));
631         _e_main_shutdown(-1);
632      }
633    TS("E_Scale Init Done");
634    _e_main_shutdown_push(e_scale_shutdown);
635
636    if (e_config->show_splash)
637      {
638         TS("E_Splash Init");
639         if (!e_init_init())
640           {
641              e_error_message_show(_("Enlightenment cannot set up its init screen.\n"));
642              _e_main_shutdown(-1);
643           }
644         TS("E_Splash Init Done");
645         _e_main_shutdown_push(e_init_shutdown);
646      }
647    if (!((!e_config->show_splash) || (after_restart)))
648      e_init_show();
649
650    if (!really_know)
651      {
652         TS("Test File Format Support");
653         _e_main_test_formats();
654         TS("Test File Format Support Done");
655      }
656    else
657      {
658         efreet_icon_extension_add(".svg");
659         efreet_icon_extension_add(".jpg");
660         efreet_icon_extension_add(".png");
661         efreet_icon_extension_add(".edj");
662      }
663
664    if (e_config->show_splash)
665      e_init_status_set(_("Setup ACPI"));
666    TS("E_Acpi Init");
667    e_acpi_init();
668    TS("E_Acpi Init Done");
669    _e_main_shutdown_push(e_acpi_shutdown);
670
671    if (e_config->show_splash)
672      e_init_status_set(_("Setup Backlight"));
673    TS("E_Backlight Init");
674    if (!e_backlight_init())
675      {
676         e_error_message_show(_("Enlightenment cannot configure the backlight.\n"));
677         _e_main_shutdown(-1);
678      }
679    TS("E_Backlight Init Done");
680
681    if (e_config->show_splash)
682      e_init_status_set(_("Setup DPMS"));
683    TS("E_Dpms Init");
684    if (!e_dpms_init())
685      {
686         e_error_message_show(_("Enlightenment cannot configure the DPMS settings.\n"));
687         _e_main_shutdown(-1);
688      }
689    TS("E_Dpms Init Done");
690    _e_main_shutdown_push(e_dpms_shutdown);
691
692    if (e_config->show_splash)
693      e_init_status_set(_("Setup Powersave Modes"));
694    TS("E_Powersave Init");
695    if (!e_powersave_init())
696      {
697         e_error_message_show(_("Enlightenment cannot set up its powersave modes.\n"));
698         _e_main_shutdown(-1);
699      }
700    TS("E_Powersave Init Done");
701    _e_main_shutdown_push(e_powersave_shutdown);
702
703    if (e_config->show_splash)
704      e_init_status_set(_("Setup Desklock"));
705    TS("E_Desklock Init");
706    if (!e_desklock_init())
707      {
708         e_error_message_show(_("Enlightenment cannot set up its desk locking system.\n"));
709         _e_main_shutdown(-1);
710      }
711    TS("E_Desklock Init Done");
712    _e_main_shutdown_push(e_desklock_shutdown);
713
714    if (waslocked || (locked && ((!after_restart) || (!getenv("E_DESKLOCK_UNLOCKED")))))
715      e_desklock_show(EINA_TRUE);
716
717    if (e_config->show_splash)
718      e_init_status_set(_("Setup Paths"));
719    TS("Efreet Paths");
720    _e_main_efreet_paths_init();
721    TS("Efreet Paths Done");
722
723    if (e_config->show_splash)
724      e_init_status_set(_("Setup System Controls"));
725    TS("E_Sys Init");
726    if (!e_sys_init())
727      {
728         e_error_message_show(_("Enlightenment cannot initialize the System Command system.\n"));
729         _e_main_shutdown(-1);
730      }
731    TS("E_Sys Init Done");
732    _e_main_shutdown_push(e_sys_shutdown);
733
734    if (e_config->show_splash)
735      e_init_status_set(_("Setup Execution System"));
736    TS("E_Exec Init");
737    if (!e_exec_init())
738      {
739         e_error_message_show(_("Enlightenment cannot set up its exec system.\n"));
740         _e_main_shutdown(-1);
741      }
742    TS("E_Exec Init Done");
743
744    TS("E_Comp Freeze");
745    e_comp_all_freeze();
746    TS("E_Comp Freeze Done");
747
748    if (e_config->show_splash)
749      e_init_status_set(_("Setup Filemanager"));
750    TS("E_Fm2 Init");
751    if (!e_fm2_init())
752      {
753         e_error_message_show(_("Enlightenment cannot initialize the File manager.\n"));
754         _e_main_shutdown(-1);
755      }
756    TS("E_Fm2 Init Done");
757    _e_main_shutdown_push(e_fm2_shutdown);
758
759    if (e_config->show_splash)
760      e_init_status_set(_("Setup Message System"));
761    TS("E_Msg Init");
762    if (!e_msg_init())
763      {
764         e_error_message_show(_("Enlightenment cannot set up its msg system.\n"));
765         _e_main_shutdown(-1);
766      }
767    TS("E_Msg Init Done");
768    _e_main_shutdown_push(e_msg_shutdown);
769
770    if (e_config->show_splash)
771      e_init_status_set(_("Setup Grab Input Handling"));
772    TS("E_Grabinput Init");
773    if (!e_grabinput_init())
774      {
775         e_error_message_show(_("Enlightenment cannot set up its grab input handling system.\n"));
776         _e_main_shutdown(-1);
777      }
778    TS("E_Grabinput Init Done");
779    _e_main_shutdown_push(e_grabinput_shutdown);
780
781    if (e_config->show_splash)
782      e_init_status_set(_("Setup Modules"));
783    TS("E_Module Init");
784    if (!e_module_init())
785      {
786         e_error_message_show(_("Enlightenment cannot set up its module system.\n"));
787         _e_main_shutdown(-1);
788      }
789    TS("E_Module Init Done");
790    _e_main_shutdown_push(e_module_shutdown);
791
792    if (e_config->show_splash)
793      e_init_status_set(_("Setup Remembers"));
794    TS("E_Remember Init");
795    if (!e_remember_init(after_restart ? E_STARTUP_RESTART : E_STARTUP_START))
796      {
797         e_error_message_show(_("Enlightenment cannot setup remember settings.\n"));
798         _e_main_shutdown(-1);
799      }
800    TS("E_Remember Init Done");
801    _e_main_shutdown_push(e_remember_shutdown);
802
803    if (e_config->show_splash)
804      e_init_status_set(_("Setup Color Classes"));
805    TS("E_Color_Class Init");
806    if (!e_color_class_init())
807      {
808         e_error_message_show(_("Enlightenment cannot set up its color class system.\n"));
809         _e_main_shutdown(-1);
810      }
811    TS("E_Color_Class Init Done");
812    _e_main_shutdown_push(e_color_class_shutdown);
813
814    if (e_config->show_splash)
815      e_init_status_set(_("Setup Gadcon"));
816    TS("E_Gadcon Init");
817    if (!e_gadcon_init())
818      {
819         e_error_message_show(_("Enlightenment cannot set up its gadget control system.\n"));
820         _e_main_shutdown(-1);
821      }
822    TS("E_Gadcon Init Done");
823    _e_main_shutdown_push(e_gadcon_shutdown);
824
825    if (e_config->show_splash)
826      e_init_status_set(_("Setup Toolbars"));
827    TS("E_Toolbar Init");
828    if (!e_toolbar_init())
829      {
830         e_error_message_show(_("Enlightenment cannot set up its toolbars.\n"));
831         _e_main_shutdown(-1);
832      }
833    TS("E_Toolbar Init Done");
834    _e_main_shutdown_push(e_toolbar_shutdown);
835
836    if (e_config->show_splash)
837      e_init_status_set(_("Setup Wallpaper"));
838    TS("E_Bg Init");
839    if (!e_bg_init())
840      {
841         e_error_message_show(_("Enlightenment cannot set up its desktop background system.\n"));
842         _e_main_shutdown(-1);
843      }
844    TS("E_Bg Init Done");
845    _e_main_shutdown_push(e_bg_shutdown);
846
847    if (e_config->show_splash)
848      e_init_status_set(_("Setup Mouse"));
849    TS("E_Mouse Init");
850    if (!e_mouse_update())
851      {
852         e_error_message_show(_("Enlightenment cannot configure the mouse settings.\n"));
853         _e_main_shutdown(-1);
854      }
855    TS("E_Mouse Init Done");
856
857    if (e_config->show_splash)
858      e_init_status_set(_("Setup Bindings"));
859    TS("E_Bindings Init");
860    if (!e_bindings_init())
861      {
862         e_error_message_show(_("Enlightenment cannot set up its bindings system.\n"));
863         _e_main_shutdown(-1);
864      }
865    TS("E_Bindings Init Done");
866    _e_main_shutdown_push(e_bindings_shutdown);
867
868    if (e_config->show_splash)
869      e_init_status_set(_("Setup Thumbnailer"));
870    TS("E_Thumb Init");
871    if (!e_thumb_init())
872      {
873         e_error_message_show(_("Enlightenment cannot initialize the Thumbnailing system.\n"));
874         _e_main_shutdown(-1);
875      }
876    TS("E_Thumb Init Done");
877    _e_main_shutdown_push(e_thumb_shutdown);
878
879    TS("E_Icon Init");
880    if (!e_icon_init())
881      {
882         e_error_message_show(_("Enlightenment cannot initialize the Icon Cache system.\n"));
883         _e_main_shutdown(-1);
884      }
885    TS("E_Icon Init Done");
886    _e_main_shutdown_push(e_icon_shutdown);
887
888    TS("E_Update Init");
889    if (!e_update_init())
890      {
891         e_error_message_show(_("Enlightenment cannot initialize the Update system.\n"));
892         _e_main_shutdown(-1);
893      }
894    TS("E_Update Init Done");
895    _e_main_shutdown_push(e_update_shutdown);
896
897    if (e_config->show_splash)
898      e_init_status_set(_("Setup Desktop Environment"));
899    TS("E_Deskenv Init");
900    if (!e_deskenv_init())
901      {
902         e_error_message_show(_("Enlightenment cannot initialize its desktop environment.\n"));
903         _e_main_shutdown(-1);
904      }
905    TS("E_Deskenv Init Done");
906    _e_main_shutdown_push(e_deskenv_shutdown);
907
908    if (e_config->show_splash)
909      e_init_status_set(_("Setup File Ordering"));
910    TS("E_Order Init");
911    if (!e_order_init())
912      {
913         e_error_message_show(_("Enlightenment cannot set up its order file system.\n"));
914         _e_main_shutdown(-1);
915      }
916    TS("E_Order Init Done");
917    _e_main_shutdown_push(e_order_shutdown);
918
919    TS("Add Idler For X Flush");
920    _idle_flush = ecore_idle_enterer_add(_e_main_cb_x_flusher, NULL);
921    TS("Add Idler For X Flush Done");
922
923    TS("E_Manager Keys Grab");
924    e_managers_keys_grab();
925    TS("E_Manager Keys Grab Done");
926
927    if (e_config->show_splash)
928      e_init_status_set(_("Load Modules"));
929    TS("Load Modules");
930    _e_main_modules_load(safe_mode);
931    TS("Load Modules Done");
932
933    TS("Run Startup Apps");
934    if (!nostartup)
935      {
936         if (after_restart)
937           e_startup(E_STARTUP_RESTART);
938         else
939           e_startup(E_STARTUP_START);
940      }
941    TS("Run Startup Apps Done");
942
943    if (e_config->show_splash && (!after_restart))
944      ecore_timer_add(2.0, _e_main_cb_startup_fake_end, NULL);
945
946    TS("E_Comp Thaw");
947    e_comp_all_thaw();
948    TS("E_Comp Thaw Done");
949
950    TS("E_Test Init");
951    e_test();
952    TS("E_Test Done");
953
954    if (e_config->show_splash)
955      e_init_status_set(_("Setup Shelves"));
956    TS("E_Shelf Init");
957    if (!e_shelf_init())
958      {
959         e_error_message_show(_("Enlightenment cannot set up its module system.\n"));
960         _e_main_shutdown(-1);
961      }
962    TS("E_Shelf Init Done");
963
964    ecore_idle_enterer_before_add(_e_main_shelf_init_job, NULL);
965
966    _idle_after = ecore_idle_enterer_add(_e_main_cb_idle_after, NULL);
967
968    if (e_config->show_splash)
969      e_init_status_set(_("Almost Done"));
970
971    starting = EINA_FALSE;
972    inloop = EINA_TRUE;
973
974    e_util_env_set("E_RESTART", "1");
975
976    TS("MAIN LOOP AT LAST");
977    if (!setjmp(x_fatal_buff))
978      ecore_main_loop_begin();
979    else
980      CRI("FATAL: X Died. Connection gone. Abbreviated Shutdown\n");
981
982    inloop = EINA_FALSE;
983    stopping = EINA_TRUE;
984
985    if (!x_fatal) e_canvas_idle_flush();
986
987    e_config_save_flush();
988    _e_main_desk_save();
989    e_remember_internal_save();
990    e_comp_internal_save();
991
992    _e_main_shutdown(0);
993
994    if (restart)
995      {
996         e_util_env_set("E_RESTART_OK", "1");
997         if (getenv("E_START_MTRACK"))
998           e_util_env_set("MTRACK", "track");
999         ecore_app_restart();
1000      }
1001
1002    e_prefix_shutdown();
1003
1004    return 0;
1005 }
1006
1007 /* FIXME: make safe to delete within a callback */
1008 EAPI E_Before_Idler *
1009 e_main_idler_before_add(int (*func)(void *data), void *data, int once)
1010 {
1011    E_Before_Idler *eb;
1012
1013    eb = calloc(1, sizeof(E_Before_Idler));
1014    eb->func = func;
1015    eb->data = data;
1016    eb->once = once;
1017    _idle_before_list = eina_list_append(_idle_before_list, eb);
1018    return eb;
1019 }
1020
1021 EAPI void
1022 e_main_idler_before_del(E_Before_Idler *eb)
1023 {
1024    eb->delete_me = 1;
1025 }
1026
1027 EAPI double
1028 e_main_ts(const char *str)
1029 {
1030    double ret;
1031    t1 = ecore_time_unix_get();
1032    printf("ESTART: %1.5f [%1.5f] - %s\n", t1 - t0, t1 - t2, str);
1033    ret = t1 - t2;
1034    t2 = t1;
1035    return ret;
1036 }
1037
1038 /* local functions */
1039 static void
1040 _e_main_shutdown(int errcode)
1041 {
1042    int i = 0;
1043
1044    printf("E19: Begin Shutdown Procedure!\n");
1045
1046    if (_idle_before) ecore_idle_enterer_del(_idle_before);
1047    _idle_before = NULL;
1048    if (_idle_after) ecore_idle_enterer_del(_idle_after);
1049    _idle_after = NULL;
1050    if (_idle_flush) ecore_idle_enterer_del(_idle_flush);
1051    _idle_flush = NULL;
1052
1053    for (i = (_e_main_lvl - 1); i >= 0; i--)
1054      (*_e_main_shutdown_func[i])();
1055    if (errcode < 0) exit(errcode);
1056 }
1057
1058 static void
1059 _e_main_shutdown_push(int (*func)(void))
1060 {
1061    _e_main_lvl++;
1062    if (_e_main_lvl > MAX_LEVEL)
1063      {
1064         _e_main_lvl--;
1065         e_error_message_show("WARNING: too many init levels. MAX = %i\n",
1066                              MAX_LEVEL);
1067         return;
1068      }
1069    _e_main_shutdown_func[_e_main_lvl - 1] = func;
1070 }
1071
1072 static void
1073 _e_main_parse_arguments(int argc, char **argv)
1074 {
1075    char *s = NULL;
1076    int i = 0;
1077
1078    /* handle some command-line parameters */
1079    for (i = 1; i < argc; i++)
1080      {
1081         if ((!strcmp(argv[i], "-display")) && (i < (argc - 1)))
1082           {
1083              i++;
1084              e_util_env_set("DISPLAY", argv[i]);
1085           }
1086         else if ((!strcmp(argv[i], "-fake-xinerama-screen")) && (i < (argc - 1)))
1087           {
1088              int x, y, w, h;
1089
1090              i++;
1091              if (sscanf(argv[i], "%ix%i+%i+%i", &w, &h, &x, &y) == 4)
1092                e_xinerama_fake_screen_add(x, y, w, h);
1093           }
1094         else if (!strcmp(argv[i], "-good"))
1095           {
1096              good = EINA_TRUE;
1097              evil = EINA_FALSE;
1098              printf("LA LA LA\n");
1099           }
1100         else if (!strcmp(argv[i], "-evil"))
1101           {
1102              good = EINA_FALSE;
1103              evil = EINA_TRUE;
1104              printf("MUHAHAHAHHAHAHAHAHA\n");
1105           }
1106         else if (!strcmp(argv[i], "-psychotic"))
1107           {
1108              good = EINA_TRUE;
1109              evil = EINA_TRUE;
1110              printf("MUHAHALALALALALALALA\n");
1111           }
1112         else if ((!strcmp(argv[i], "-profile")) && (i < (argc - 1)))
1113           {
1114              i++;
1115              if (!getenv("E_CONF_PROFILE"))
1116                e_util_env_set("E_CONF_PROFILE", argv[i]);
1117           }
1118         else if (!strcmp(argv[i], "-i-really-know-what-i-am-doing-and-accept-full-responsibility-for-it"))
1119           really_know = EINA_TRUE;
1120         else if (!strcmp(argv[i], "-locked"))
1121           locked = EINA_TRUE;
1122         else if (!strcmp(argv[i], "-nopause"))
1123           e_nopause = EINA_TRUE;
1124         else if ((!strcmp(argv[i], "-h")) ||
1125                  (!strcmp(argv[i], "-help")) ||
1126                  (!strcmp(argv[i], "--help")))
1127           {
1128              printf
1129                (_(
1130                  "Options:\n"
1131                  "\t-display DISPLAY\n"
1132                  "\t\tConnect to display named DISPLAY.\n"
1133                  "\t\tEG: -display :1.0\n"
1134                  "\t-fake-xinerama-screen WxH+X+Y\n"
1135                  "\t\tAdd a FAKE xinerama screen (instead of the real ones)\n"
1136                  "\t\tgiven the geometry. Add as many as you like. They all\n"
1137                  "\t\treplace the real xinerama screens, if any. This can\n"
1138                  "\t\tbe used to simulate xinerama.\n"
1139                  "\t\tEG: -fake-xinerama-screen 800x600+0+0 -fake-xinerama-screen 800x600+800+0\n"
1140                  "\t-profile CONF_PROFILE\n"
1141                  "\t\tUse the configuration profile CONF_PROFILE instead of the user selected default or just \"default\".\n"
1142                  "\t-good\n"
1143                  "\t\tBe good.\n"
1144                  "\t-evil\n"
1145                  "\t\tBe evil.\n"
1146                  "\t-psychotic\n"
1147                  "\t\tBe psychotic.\n"
1148                  "\t-locked\n"
1149                  "\t\tStart with desklock on, so password will be asked.\n"
1150                  "\t-i-really-know-what-i-am-doing-and-accept-full-responsibility-for-it\n"
1151                  "\t\tIf you need this help, you don't need this option.\n"
1152                  )
1153                );
1154              _e_main_shutdown(-1);
1155           }
1156      }
1157
1158    /* fix up DISPLAY to be :N.0 if no .screen is in it */
1159    s = getenv("DISPLAY");
1160    if (s)
1161      {
1162         char *p, buff[4096];
1163
1164         if (!(p = strrchr(s, ':')))
1165           {
1166              snprintf(buff, sizeof(buff), "%s:0.0", s);
1167              e_util_env_set("DISPLAY", buff);
1168           }
1169         else
1170           {
1171              if (!strrchr(p, '.'))
1172                {
1173                   snprintf(buff, sizeof(buff), "%s.0", s);
1174                   e_util_env_set("DISPLAY", buff);
1175                }
1176           }
1177      }
1178
1179    /* we want to have been launched by enlightenment_start. there is a very */
1180    /* good reason we want to have been launched this way, thus check */
1181    if (!getenv("E_START"))
1182      {
1183         e_error_message_show(_("You are executing enlightenment directly. This is\n"
1184                                "bad. Please do not execute the \"enlightenment\"\n"
1185                                "binary. Use the \"enlightenment_start\" launcher. It\n"
1186                                "will handle setting up environment variables, paths,\n"
1187                                "and launching any other required services etc.\n"
1188                                "before enlightenment itself begins running.\n"));
1189         _e_main_shutdown(-1);
1190      }
1191 }
1192
1193 EINTERN void
1194 _e_main_cb_x_fatal(void *data __UNUSED__)
1195 {
1196    e_error_message_show("Lost X Connection.\n");
1197    ecore_main_loop_quit();
1198    if (!x_fatal)
1199      {
1200         x_fatal = EINA_TRUE;
1201         if (inloop) longjmp(x_fatal_buff, -99);
1202      }
1203 }
1204
1205 static Eina_Bool
1206 _e_main_cb_signal_exit(void *data __UNUSED__, int ev_type __UNUSED__, void *ev __UNUSED__)
1207 {
1208    /* called on ctrl-c, kill (pid) (also SIGINT, SIGTERM and SIGQIT) */
1209    e_sys_action_do(E_SYS_EXIT, NULL);
1210    return ECORE_CALLBACK_RENEW;
1211 }
1212
1213 static Eina_Bool
1214 _e_main_cb_signal_hup(void *data __UNUSED__, int ev_type __UNUSED__, void *ev __UNUSED__)
1215 {
1216    e_sys_action_do(E_SYS_RESTART, NULL);
1217    return ECORE_CALLBACK_RENEW;
1218 }
1219
1220 static Eina_Bool
1221 _e_main_cb_signal_user(void *data __UNUSED__, int ev_type __UNUSED__, void *ev)
1222 {
1223    Ecore_Event_Signal_User *e = ev;
1224
1225    if (e->number == 1)
1226      {
1227 //        E_Action *a = e_action_find("configuration");
1228 //        if ((a) && (a->func.go)) a->func.go(NULL, NULL);
1229      }
1230    else if (e->number == 2)
1231      {
1232         // comp module has its own handler for this for enabling/disabling fps debug
1233      }
1234    return ECORE_CALLBACK_RENEW;
1235
1236 }
1237
1238 static int
1239 _e_main_dirs_init(void)
1240 {
1241    const char *base;
1242    const char *dirs[] =
1243    {
1244       "images",
1245       "fonts",
1246       "themes",
1247       "icons",
1248       "backgrounds",
1249       "applications",
1250       "applications/menu",
1251       "applications/menu/favorite",
1252       "applications/menu/all",
1253       "applications/bar",
1254       "applications/bar/default",
1255       "applications/startup",
1256       "applications/restart",
1257       "applications/trash",
1258       "applications/desk-lock",
1259       "applications/desk-unlock",
1260       "modules",
1261       "config",
1262       "locale",
1263       "input_methods",
1264       NULL
1265    };
1266
1267    base = e_user_dir_get();
1268    if (ecore_file_mksubdirs(base, dirs) != sizeof(dirs) / sizeof(dirs[0]) - 1)
1269      {
1270         e_error_message_show("Could not create one of the required "
1271                              "subdirectories of '%s'\n", base);
1272         return 0;
1273      }
1274
1275    return 1;
1276 }
1277
1278 static int
1279 _e_main_dirs_shutdown(void)
1280 {
1281    return 1;
1282 }
1283
1284 static int
1285 _e_main_path_init(void)
1286 {
1287    char buf[PATH_MAX];
1288
1289    /* setup data paths */
1290    path_data = e_path_new();
1291    if (!path_data)
1292      {
1293         e_error_message_show("Cannot allocate path for path_data\n");
1294         return 0;
1295      }
1296    e_prefix_data_concat_static(buf, "data");
1297    e_path_default_path_append(path_data, buf);
1298    e_path_user_path_set(path_data, &(e_config->path_append_data));
1299
1300    /* setup image paths */
1301    path_images = e_path_new();
1302    if (!path_images)
1303      {
1304         e_error_message_show("Cannot allocate path for path_images\n");
1305         return 0;
1306      }
1307    e_user_dir_concat_static(buf, "/images");
1308    e_path_default_path_append(path_images, buf);
1309    e_prefix_data_concat_static(buf, "data/images");
1310    e_path_default_path_append(path_images, buf);
1311    e_path_user_path_set(path_images, &(e_config->path_append_images));
1312
1313    /* setup font paths */
1314    path_fonts = e_path_new();
1315    if (!path_fonts)
1316      {
1317         e_error_message_show("Cannot allocate path for path_fonts\n");
1318         return 0;
1319      }
1320    e_user_dir_concat_static(buf, "/fonts");
1321    e_path_default_path_append(path_fonts, buf);
1322    e_prefix_data_concat_static(buf, "data/fonts");
1323    e_path_default_path_append(path_fonts, buf);
1324    e_path_user_path_set(path_fonts, &(e_config->path_append_fonts));
1325
1326    /* setup icon paths */
1327    path_icons = e_path_new();
1328    if (!path_icons)
1329      {
1330         e_error_message_show("Cannot allocate path for path_icons\n");
1331         return 0;
1332      }
1333    e_user_dir_concat_static(buf, "/icons");
1334    e_path_default_path_append(path_icons, buf);
1335    e_prefix_data_concat_static(buf, "data/icons");
1336    e_path_default_path_append(path_icons, buf);
1337    e_path_user_path_set(path_icons, &(e_config->path_append_icons));
1338
1339    /* setup module paths */
1340    path_modules = e_path_new();
1341    if (!path_modules)
1342      {
1343         e_error_message_show("Cannot allocate path for path_modules\n");
1344         return 0;
1345      }
1346    e_user_dir_concat_static(buf, "/modules");
1347    e_path_default_path_append(path_modules, buf);
1348    snprintf(buf, sizeof(buf), "%s/enlightenment/modules", e_prefix_lib_get());
1349    e_path_default_path_append(path_modules, buf);
1350    /* FIXME: eventually this has to go - moduels should have installers that
1351     * add appropriate install paths (if not installed to user homedir) to
1352     * e's module search dirs
1353     */
1354    snprintf(buf, sizeof(buf), "%s/enlightenment/modules_extra", e_prefix_lib_get());
1355    e_path_default_path_append(path_modules, buf);
1356    e_path_user_path_set(path_modules, &(e_config->path_append_modules));
1357
1358    /* setup background paths */
1359    path_backgrounds = e_path_new();
1360    if (!path_backgrounds)
1361      {
1362         e_error_message_show("Cannot allocate path for path_backgrounds\n");
1363         return 0;
1364      }
1365    e_user_dir_concat_static(buf, "/backgrounds");
1366    e_path_default_path_append(path_backgrounds, buf);
1367    e_prefix_data_concat_static(buf, "data/backgrounds");
1368    e_path_default_path_append(path_backgrounds, buf);
1369    e_path_user_path_set(path_backgrounds, &(e_config->path_append_backgrounds));
1370
1371    path_messages = e_path_new();
1372    if (!path_messages)
1373      {
1374         e_error_message_show("Cannot allocate path for path_messages\n");
1375         return 0;
1376      }
1377    e_user_dir_concat_static(buf, "/locale");
1378    e_path_default_path_append(path_messages, buf);
1379    e_path_default_path_append(path_messages, e_prefix_locale_get());
1380    e_path_user_path_set(path_messages, &(e_config->path_append_messages));
1381
1382    return 1;
1383 }
1384
1385 static int
1386 _e_main_path_shutdown(void)
1387 {
1388    if (path_data)
1389      {
1390         e_object_del(E_OBJECT(path_data));
1391         path_data = NULL;
1392      }
1393    if (path_images)
1394      {
1395         e_object_del(E_OBJECT(path_images));
1396         path_images = NULL;
1397      }
1398    if (path_fonts)
1399      {
1400         e_object_del(E_OBJECT(path_fonts));
1401         path_fonts = NULL;
1402      }
1403    if (path_icons)
1404      {
1405         e_object_del(E_OBJECT(path_icons));
1406         path_icons = NULL;
1407      }
1408    if (path_modules)
1409      {
1410         e_object_del(E_OBJECT(path_modules));
1411         path_modules = NULL;
1412      }
1413    if (path_backgrounds)
1414      {
1415         e_object_del(E_OBJECT(path_backgrounds));
1416         path_backgrounds = NULL;
1417      }
1418    if (path_messages)
1419      {
1420         e_object_del(E_OBJECT(path_messages));
1421         path_messages = NULL;
1422      }
1423    return 1;
1424 }
1425
1426 static void
1427 _e_main_test_formats(void)
1428 {
1429    Evas *evas;
1430    Ecore_Evas *ee;
1431    Evas_Object *im, *txt;
1432    Evas_Coord tw, th;
1433    char buff[PATH_MAX];
1434
1435    if (e_config->show_splash)
1436      e_init_status_set(_("Testing Format Support"));
1437
1438    if (!(ee = ecore_evas_buffer_new(1, 1)))
1439      {
1440         e_error_message_show(_("Enlightenment found Evas can't create a buffer canvas. Please check\n"
1441                                "Evas has Software Buffer engine support.\n"));
1442         _e_main_shutdown(-1);
1443      }
1444    e_canvas_add(ee);
1445    evas = ecore_evas_get(ee);
1446    im = evas_object_image_add(evas);
1447
1448    e_prefix_data_concat_static(buff, "data/images/test.svg");
1449    evas_object_image_file_set(im, buff, NULL);
1450    if (evas_object_image_load_error_get(im) != EVAS_LOAD_ERROR_NONE)
1451      {
1452         e_error_message_show(_("Enlightenment found Evas can't load SVG files. "
1453                                "Check Evas has SVG loader support.\n"));
1454      }
1455    else
1456      efreet_icon_extension_add(".svg");
1457
1458    e_prefix_data_concat_static(buff, "data/images/test.jpg");
1459    evas_object_image_file_set(im, buff, NULL);
1460    if (evas_object_image_load_error_get(im) != EVAS_LOAD_ERROR_NONE)
1461      {
1462         e_error_message_show(_("Enlightenment found Evas can't load JPEG files. "
1463                                "Check Evas has JPEG loader support.\n"));
1464         _e_main_shutdown(-1);
1465      }
1466    efreet_icon_extension_add(".jpg");
1467
1468    e_prefix_data_concat_static(buff, "data/images/test.png");
1469    evas_object_image_file_set(im, buff, NULL);
1470    if (evas_object_image_load_error_get(im) != EVAS_LOAD_ERROR_NONE)
1471      {
1472         e_error_message_show(_("Enlightenment found Evas can't load PNG files. "
1473                                "Check Evas has PNG loader support.\n"));
1474         _e_main_shutdown(-1);
1475      }
1476    efreet_icon_extension_add(".png");
1477
1478    e_prefix_data_concat_static(buff, "data/images/test.edj");
1479    evas_object_image_file_set(im, buff, "images/0");
1480    if (evas_object_image_load_error_get(im) != EVAS_LOAD_ERROR_NONE)
1481      {
1482         e_error_message_show(_("Enlightenment found Evas can't load EET files. "
1483                                "Check Evas has EET loader support.\n"));
1484         _e_main_shutdown(-1);
1485      }
1486    efreet_icon_extension_add(".edj");
1487
1488    evas_object_del(im);
1489
1490    txt = evas_object_text_add(evas);
1491    evas_object_text_font_set(txt, "Sans", 10);
1492    evas_object_text_text_set(txt, "Hello");
1493    evas_object_geometry_get(txt, NULL, NULL, &tw, &th);
1494    if ((tw <= 0) && (th <= 0))
1495      {
1496         e_error_message_show(_("Enlightenment found Evas can't load the 'Sans' font. Check Evas has fontconfig\n"
1497                                "support and system fontconfig defines a 'Sans' font.\n"));
1498         _e_main_shutdown(-1);
1499      }
1500    evas_object_del(txt);
1501    e_canvas_del(ee);
1502    ecore_evas_free(ee);
1503 }
1504
1505 static int
1506 _e_main_screens_init(void)
1507 {
1508    TS("\tscreens: manager");
1509    if (!e_manager_init()) return 0;
1510
1511    TS("\tscreens: client");
1512    if (!e_client_init()) return 0;
1513    TS("\tscreens: win");
1514    if (!e_win_init()) return 0;
1515    TS("E_Xkb Init");
1516    if (!e_xkb_init())
1517      {
1518         e_error_message_show(_("Enlightenment cannot setup XKB Keyboard layouts.\n"));
1519         _e_main_shutdown(-1);
1520      }
1521    TS("E_Xkb Init Done");
1522
1523    TS("Compositor Init");
1524    if (!e_comp_init())
1525      {
1526         e_error_message_show(_("Enlightenment cannot create a compositor.\n"));
1527         _e_main_shutdown(-1);
1528      }
1529
1530    _e_main_desk_restore();
1531
1532    if (e_config->show_splash)
1533      e_init_status_set(_("Setup DND"));
1534    TS("E_Dnd Init");
1535    if (!e_dnd_init())
1536      {
1537         e_error_message_show(_("Enlightenment cannot set up its dnd system.\n"));
1538         _e_main_shutdown(-1);
1539      }
1540    TS("E_Dnd Init Done");
1541    _e_main_shutdown_push(e_dnd_shutdown);
1542
1543    return 1;
1544 }
1545
1546 static int
1547 _e_main_screens_shutdown(void)
1548 {
1549    e_win_shutdown();
1550    e_menu_shutdown();
1551    e_shelf_shutdown();
1552    e_comp_shutdown();
1553    e_client_shutdown();
1554    e_exehist_shutdown();
1555    e_backlight_shutdown();
1556    e_exec_shutdown();
1557 // ecore_evas closes evas - deletes objs - deletes fm widgets which tries to
1558 // ipc to slave to stop monitoring - but ipc has been shut down. dont shut
1559 // down.
1560 //   e_desk_shutdown();
1561 //   e_zone_shutdown();
1562 //   e_container_shutdown();
1563 //   e_manager_shutdown();
1564    return 1;
1565 }
1566
1567 static void
1568 _e_main_desk_save(void)
1569 {
1570    E_Comp *c;
1571    const Eina_List *l;
1572    char env[1024], name[1024];
1573
1574    EINA_LIST_FOREACH(e_comp_list(), l, c)
1575      {
1576         Eina_List *zl;
1577         E_Zone *zone;
1578
1579         EINA_LIST_FOREACH(c->zones, zl, zone)
1580           {
1581              snprintf(name, sizeof(name), "DESK_%d_%d", c->num, zone->num);
1582              snprintf(env, sizeof(env), "%d,%d", zone->desk_x_current, zone->desk_y_current);
1583              e_util_env_set(name, env);
1584           }
1585      }
1586 }
1587
1588 static void
1589 _e_main_desk_restore(void)
1590 {
1591    E_Comp *c;
1592    const Eina_List *l, *ll;
1593    E_Zone *zone;
1594    char *env;
1595    char name[1024];
1596
1597    EINA_LIST_FOREACH(e_comp_list(), l, c)
1598       EINA_LIST_FOREACH(c->zones, ll, zone)
1599         {
1600            E_Desk *desk;
1601            int desk_x, desk_y;
1602
1603            snprintf(name, sizeof(name), "DESK_%d_%d", c->num, zone->num);
1604            env = getenv(name);
1605            if (!env) continue;
1606            if (!sscanf(env, "%d,%d", &desk_x, &desk_y)) continue;
1607            desk = e_desk_at_xy_get(zone, desk_x, desk_y);
1608            if (!desk) continue;
1609            e_desk_show(desk);
1610         }
1611 }
1612
1613 static void
1614 _e_main_efreet_paths_init(void)
1615 {
1616    Eina_List **list;
1617
1618    if ((list = efreet_icon_extra_list_get()))
1619      {
1620         char buff[PATH_MAX];
1621
1622         e_user_dir_concat_static(buff, "icons");
1623         *list = eina_list_prepend(*list, (void *)eina_stringshare_add(buff));
1624         e_prefix_data_concat_static(buff, "data/icons");
1625         *list = eina_list_prepend(*list, (void *)eina_stringshare_add(buff));
1626      }
1627 }
1628
1629 static Eina_Bool
1630 _e_main_modules_load_after(void *d EINA_UNUSED, int type EINA_UNUSED, void *ev EINA_UNUSED)
1631 {
1632    e_int_config_modules(NULL, NULL);
1633    E_FREE_FUNC(mod_init_end, ecore_event_handler_del);
1634    return ECORE_CALLBACK_RENEW;
1635 }
1636
1637 static void
1638 _e_main_modules_load(Eina_Bool safe_mode)
1639 {
1640    if (!safe_mode)
1641      e_module_all_load();
1642    else
1643      {
1644         E_Module *m;
1645         char *crashmodule;
1646
1647         crashmodule = getenv("E_MODULE_LOAD");
1648         if (crashmodule) m = e_module_new(crashmodule);
1649
1650         if ((crashmodule) && (m))
1651           {
1652              e_module_disable(m);
1653              e_object_del(E_OBJECT(m));
1654
1655              e_error_message_show
1656                (_("Enlightenment crashed early on start and has<br>"
1657                   "been restarted. There was an error loading the<br>"
1658                   "module named: %s. This module has been disabled<br>"
1659                   "and will not be loaded."), crashmodule);
1660              e_util_dialog_show
1661                (_("Enlightenment crashed early on start and has been restarted"),
1662                _("Enlightenment crashed early on start and has been restarted.<br>"
1663                  "There was an error loading the module named: %s<br><br>"
1664                  "This module has been disabled and will not be loaded."), crashmodule);
1665              e_module_all_load();
1666           }
1667         else
1668           {
1669              e_error_message_show
1670                (_("Enlightenment crashed early on start and has<br>"
1671                   "been restarted. All modules have been disabled<br>"
1672                   "and will not be loaded to help remove any problem<br>"
1673                   "modules from your configuration. The module<br>"
1674                   "configuration dialog should let you select your<br>"
1675                   "modules again.\n"));
1676              e_util_dialog_show
1677                (_("Enlightenment crashed early on start and has been restarted"),
1678                _("Enlightenment crashed early on start and has been restarted.<br>"
1679                  "All modules have been disabled and will not be loaded to help<br>"
1680                  "remove any problem modules from your configuration.<br><br>"
1681                  "The module configuration dialog should let you select your<br>"
1682                  "modules again."));
1683           }
1684         mod_init_end = ecore_event_handler_add(E_EVENT_MODULE_INIT_END, _e_main_modules_load_after, NULL);
1685      }
1686 }
1687
1688 static Eina_Bool
1689 _e_main_cb_idle_before(void *data __UNUSED__)
1690 {
1691    Eina_List *l, *pl;
1692    E_Before_Idler *eb;
1693
1694    e_menu_idler_before();
1695    e_client_idler_before();
1696    e_pointer_idler_before();
1697    EINA_LIST_FOREACH(_idle_before_list, l, eb)
1698      {
1699         if (!eb->delete_me)
1700           {
1701              if (!eb->func(eb->data)) eb->delete_me = 1;
1702           }
1703      }
1704    EINA_LIST_FOREACH_SAFE(_idle_before_list, pl, l, eb)
1705      {
1706         if ((eb->once) || (eb->delete_me))
1707           {
1708              _idle_before_list =
1709                eina_list_remove_list(_idle_before_list, pl);
1710              free(eb);
1711           }
1712      }
1713    edje_thaw();
1714    return ECORE_CALLBACK_RENEW;
1715 }
1716
1717 static Eina_Bool
1718 _e_main_cb_idle_after(void *data __UNUSED__)
1719 {
1720    static int first_idle = 1;
1721
1722    edje_freeze();
1723
1724 #ifdef E19_RELEASE_BUILD
1725    if (first_idle)
1726      {
1727         TS("SLEEP");
1728         first_idle = 0;
1729         e_precache_end = EINA_TRUE;
1730      }
1731 #else
1732    if (first_idle++ < 60)
1733      {
1734         TS("SLEEP");
1735         if (!first_idle)
1736           e_precache_end = EINA_TRUE;
1737      }
1738 #endif
1739
1740    return ECORE_CALLBACK_RENEW;
1741 }
1742
1743 static Eina_Bool
1744 _e_main_cb_x_flusher(void *data __UNUSED__)
1745 {
1746    eet_clearcache();
1747    ecore_x_flush();
1748    return ECORE_CALLBACK_RENEW;
1749 }
1750
1751 static Eina_Bool
1752 _e_main_cb_startup_fake_end(void *data __UNUSED__)
1753 {
1754    e_init_hide();
1755    return ECORE_CALLBACK_CANCEL;
1756 }
1757