3 # include <sys/prctl.h>
6 # include <systemd/sd-daemon.h>
15 t1 = ecore_time_unix_get(); \
16 printf("ESTART: %1.5f [%1.5f] - %s\n", t1 - t0, t1 - t2, x); \
19 static double t0, t1, t2;
24 * i need to make more use of these when i'm baffled as to when something is
27 * void *(*__malloc_hook)(size_t size, const void *caller);
29 * void *(*__realloc_hook)(void *ptr, size_t size, const void *caller);
31 * void *(*__memalign_hook)(size_t alignment, size_t size,
32 * const void *caller);
34 * void (*__free_hook)(void *ptr, const void *caller);
36 * void (*__malloc_initialize_hook)(void);
38 * void (*__after_morecore_hook)(void);
41 static void my_init_hook(void);
42 static void my_free_hook(void *p, const void *caller);
44 static void (*old_free_hook)(void *ptr, const void *caller) = NULL;
45 void (*__free_hook)(void *ptr, const void *caller);
47 void (*__malloc_initialize_hook) (void) = my_init_hook;
51 old_free_hook = __free_hook;
52 __free_hook = my_free_hook;
55 //void *magicfree = NULL;
58 my_free_hook(void *p, const void *caller)
60 __free_hook = old_free_hook;
61 // if ((p) && (p == magicfree))
63 // printf("CAUGHT!!!!! %p ...\n", p);
67 __free_hook = my_free_hook;
71 /* local function prototypes */
72 static void _e_main_shutdown(int errcode);
73 static void _e_main_shutdown_push(int (*func)(void));
74 static void _e_main_parse_arguments(int argc, char **argv);
75 static Eina_Bool _e_main_cb_signal_exit(void *data EINA_UNUSED, int ev_type EINA_UNUSED, void *ev EINA_UNUSED);
76 static Eina_Bool _e_main_cb_signal_hup(void *data EINA_UNUSED, int ev_type EINA_UNUSED, void *ev EINA_UNUSED);
77 static Eina_Bool _e_main_cb_signal_user(void *data EINA_UNUSED, int ev_type EINA_UNUSED, void *ev);
78 static int _e_main_dirs_init(void);
79 static int _e_main_dirs_shutdown(void);
80 static int _e_main_path_init(void);
81 static int _e_main_path_shutdown(void);
82 static int _e_main_screens_init(void);
83 static int _e_main_screens_shutdown(void);
84 static void _e_main_desk_save(void);
85 static void _e_main_desk_restore(void);
86 static void _e_main_modules_load(Eina_Bool safe_mode);
87 static Eina_Bool _e_main_cb_idle_before(void *data EINA_UNUSED);
88 static Eina_Bool _e_main_cb_idle_after(void *data EINA_UNUSED);
89 static void _e_main_create_wm_ready(void);
90 static void _e_main_hooks_clean(void);
91 static void _e_main_hook_call(E_Main_Hook_Point hookpoint, void *data EINA_UNUSED);
94 static Eina_Bool really_know = EINA_FALSE;
95 static Eina_Bool inloop = EINA_FALSE;
97 static int _e_main_lvl = 0;
98 static int(*_e_main_shutdown_func[MAX_LEVEL]) (void);
100 static Ecore_Idle_Enterer *_idle_before = NULL;
101 static Ecore_Idle_Enterer *_idle_after = NULL;
103 static Ecore_Event_Handler *mod_init_end = NULL;
105 static Eina_List *hooks = NULL;
107 static int _e_main_hooks_delete = 0;
108 static int _e_main_hooks_walking = 0;
110 static Eina_Inlist *_e_main_hooks[] =
112 [E_MAIN_HOOK_MODULE_LOAD_DONE] = NULL,
113 [E_MAIN_HOOK_E_INFO_READY] = NULL
116 /* external variables */
117 E_API Eina_Bool e_precache_end = EINA_FALSE;
118 E_API Eina_Bool good = EINA_FALSE;
119 E_API Eina_Bool evil = EINA_FALSE;
120 E_API Eina_Bool starting = EINA_TRUE;
121 E_API Eina_Bool stopping = EINA_FALSE;
122 E_API Eina_Bool restart = EINA_FALSE;
123 E_API Eina_Bool e_nopause = EINA_FALSE;
124 EINTERN const char *e_first_frame = NULL;
125 EINTERN double e_first_frame_start_time = -1;
128 _xdg_check_str(const char *env, const char *str)
134 for (p = strstr(env, str); p; p++, p = strstr(p, str))
136 if ((!p[len]) || (p[len] == ':')) return EINA_TRUE;
142 _xdg_data_dirs_augment(void)
145 const char *p = e_prefix_get();
146 char newpath[4096], buf[4096];
150 s = getenv("XDG_DATA_DIRS");
153 Eina_Bool pfxdata, pfx;
155 pfxdata = !_xdg_check_str(s, e_prefix_data_get());
156 snprintf(newpath, sizeof(newpath), "%s/share", p);
157 pfx = !_xdg_check_str(s, newpath);
160 snprintf(buf, sizeof(buf), "%s%s%s%s%s",
161 pfxdata ? e_prefix_data_get() : "",
166 e_util_env_set("XDG_DATA_DIRS", buf);
171 snprintf(buf, sizeof(buf), "%s:%s/share:/usr/local/share:/usr/share", e_prefix_data_get(), p);
172 e_util_env_set("XDG_DATA_DIRS", buf);
175 s = getenv("XDG_CONFIG_DIRS");
176 snprintf(newpath, sizeof(newpath), "%s/etc/xdg", p);
179 if (!_xdg_check_str(s, newpath))
181 snprintf(buf, sizeof(buf), "%s:%s", newpath, s);
182 e_util_env_set("XDG_CONFIG_DIRS", buf);
187 snprintf(buf, sizeof(buf), "%s:/etc/xdg", newpath);
188 e_util_env_set("XDG_CONFIG_DIRS", buf);
191 if (!getenv("XDG_RUNTIME_DIR"))
195 snprintf(buf, sizeof(buf), "/tmp/xdg-XXXXXX");
197 if (!dir) dir = "/tmp";
200 e_util_env_set("XDG_RUNTIME_DIR", dir);
201 snprintf(buf, sizeof(buf), "%s/.e-deleteme", dir);
202 ecore_file_mkdir(buf);
206 /* set menu prefix so we get our e menu */
207 if (!getenv("XDG_MENU_PREFIX"))
209 e_util_env_set("XDG_MENU_PREFIX", "e-");
214 _e_main_subsystem_defer(void *data EINA_UNUSED)
219 TRACE_DS_BEGIN(MAIN:SUBSYSTEMS DEFER);
221 ecore_app_args_get(&argc, &argv);
223 /* try to init delayed subsystems */
225 TRACE_DS_BEGIN(MAIN:DEFERRED INTERNAL SUBSYSTEMS INIT);
227 TS("[DEFERRED] DPMS Init");
230 e_error_message_show(_("Enlightenment cannot set up dpms.\n"));
231 _e_main_shutdown(-1);
233 TS("[DEFERRED] DPMS Init Done");
234 _e_main_shutdown_push(e_dpms_shutdown);
236 TS("[DEFERRED] Screens Init: win");
239 e_error_message_show(_("Enlightenment cannot setup elementary trap!\n"));
241 _e_main_shutdown(-1);
243 TS("[DEFERRED] Screens Init: win Done");
245 TS("[DEFERRED] E_Dnd Init");
248 e_error_message_show(_("Enlightenment cannot set up its dnd system.\n"));
249 _e_main_shutdown(-1);
251 TS("[DEFERRED] E_Dnd Init Done");
252 _e_main_shutdown_push(e_dnd_shutdown);
254 TS("[DEFERRED] E_Scale Init");
257 e_error_message_show(_("Enlightenment cannot set up its scale system.\n"));
259 _e_main_shutdown(-1);
261 TS("[DEFERRED] E_Scale Init Done");
262 _e_main_shutdown_push(e_scale_shutdown);
264 TS("[DEFERRED] E_Test_Helper Init");
265 e_test_helper_init();
266 _e_main_shutdown_push(e_test_helper_shutdown);
267 TS("[DEFERRED] E_Test_Helper Done");
269 TS("[DEFERRED] E_INFO_SERVER Init");
270 e_info_server_init();
271 _e_main_shutdown_push(e_info_server_shutdown);
272 TS("[DEFERRED] E_INFO_SERVER Done");
275 TRACE_DS_BEGIN(MAIN:DEFERRED COMP JOB);
277 /* try to do deferred job of any subsystems*/
278 TS("[DEFERRED] Compositor's deferred job");
279 e_comp_deferred_job();
280 TS("[DEFERRED] Compositor's deferred job Done");
283 if (e_config->use_e_policy)
285 TRACE_DS_BEGIN(MAIN:DEFERRED POLICY JOB);
287 TS("[DEFERRED] E_Policy's deferred job");
288 e_policy_deferred_job();
289 TS("[DEFERRED] E_Policy's deferred job Done");
293 TRACE_DS_BEGIN(MAIN:DEFERRED MODULE JOB);
295 TS("[DEFERRED] E_Module's deferred job");
296 e_module_deferred_job();
297 TS("[DEFERRED] E_Module's deferred job Done");
302 return ECORE_CALLBACK_DONE;
306 _e_main_deferred_job_schedule(void *d EINA_UNUSED, int type EINA_UNUSED, void *ev EINA_UNUSED)
308 PRCTL("[Winsys] all modules loaded");
309 ecore_idler_add(_e_main_subsystem_defer, NULL);
310 return ECORE_CALLBACK_DONE;
313 /* externally accessible functions */
315 main(int argc, char **argv)
317 Eina_Bool safe_mode = EINA_FALSE;
318 double t = 0.0, tstart = 0.0;
319 char *s = NULL, buff[32];
320 struct sigaction action;
323 # ifdef PR_SET_PTRACER
324 # ifdef PR_SET_PTRACER_ANY
325 prctl(PR_SET_PTRACER, PR_SET_PTRACER_ANY);
330 t0 = t1 = t2 = ecore_time_unix_get();
331 printf("ESTART(main) %1.5f\n", t0);
333 TRACE_DS_BEGIN(MAIN:BEGIN STARTUP);
335 PRCTL("[Winsys] start of main");
337 /* trap deadly bug signals and allow some form of sane recovery */
338 /* or ability to gdb attach and debug at this point - better than your */
339 /* wm/desktop vanishing and not knowing what happened */
341 /* don't install SIGBUS handler */
342 /* Wayland shm sets up a sigbus handler for catching invalid shm region */
343 /* access. If we setup our sigbus handler here, then the wl-shm sigbus */
344 /* handler will not function properly */
345 if (!getenv("NOTIFY_SOCKET"))
348 action.sa_sigaction = e_sigseg_act;
349 action.sa_flags = SA_NODEFER | SA_RESETHAND | SA_SIGINFO;
350 sigemptyset(&action.sa_mask);
351 sigaction(SIGSEGV, &action, NULL);
353 action.sa_sigaction = e_sigill_act;
354 action.sa_flags = SA_NODEFER | SA_RESETHAND | SA_SIGINFO;
355 sigemptyset(&action.sa_mask);
356 sigaction(SIGILL, &action, NULL);
358 action.sa_sigaction = e_sigfpe_act;
359 action.sa_flags = SA_NODEFER | SA_RESETHAND | SA_SIGINFO;
360 sigemptyset(&action.sa_mask);
361 sigaction(SIGFPE, &action, NULL);
363 action.sa_sigaction = e_sigabrt_act;
364 action.sa_flags = SA_NODEFER | SA_RESETHAND | SA_SIGINFO;
365 sigemptyset(&action.sa_mask);
366 sigaction(SIGABRT, &action, NULL);
367 TS("Signal Trap Done");
370 t = ecore_time_unix_get();
371 s = getenv("E_START_TIME");
372 if ((s) && (!getenv("E_RESTART_OK")))
375 if ((t - tstart) < 5.0) safe_mode = EINA_TRUE;
378 snprintf(buff, sizeof(buff), "%1.1f", tstart);
379 e_util_env_set("E_START_TIME", buff);
381 if (getenv("E_START_MTRACK"))
382 e_util_env_set("MTRACK", NULL);
386 e_error_message_show(_("Enlightenment cannot initialize Eina!\n"));
387 _e_main_shutdown(-1);
389 TS("Eina Init Done");
390 _e_main_shutdown_push(eina_shutdown);
392 #ifdef OBJECT_HASH_CHECK
393 TS("E_Object Hash Init");
394 e_object_hash_init();
395 TS("E_Object Hash Init Done");
401 e_error_message_show(_("Enlightenment could not create a logging domain!\n"));
402 _e_main_shutdown(-1);
404 TS("E_Log Init Done");
405 _e_main_shutdown_push(e_log_shutdown);
407 TS("Determine Prefix");
408 if (!e_prefix_determine(argv[0]))
411 "ERROR: Enlightenment cannot determine it's installed\n"
412 " prefix from the system or argv[0].\n"
413 " This is because it is not on Linux AND has been\n"
414 " executed strangely. This is unusual.\n");
416 TS("Determine Prefix Done");
418 /* for debugging by redirecting stdout of e to a log file to tail */
419 setvbuf(stdout, NULL, _IONBF, 0);
421 TS("Parse Arguments");
422 _e_main_parse_arguments(argc, argv);
423 TS("Parse Arguments Done");
425 /*** Initialize Core EFL Libraries We Need ***/
430 e_error_message_show(_("Enlightenment cannot initialize Eet!\n"));
431 _e_main_shutdown(-1);
434 _e_main_shutdown_push(eet_shutdown);
436 /* Allow ecore to not load system modules.
437 * Without it ecore_init will block until dbus authentication
438 * and registration are complete.
440 ecore_app_no_system_modules();
445 e_error_message_show(_("Enlightenment cannot initialize Ecore!\n"));
446 _e_main_shutdown(-1);
448 TS("Ecore Init Done");
449 _e_main_shutdown_push(ecore_shutdown);
451 e_first_frame = getenv("E_FIRST_FRAME");
452 if (e_first_frame && e_first_frame[0])
453 e_first_frame_start_time = ecore_time_get();
455 e_first_frame = NULL;
460 e_error_message_show(_("Enlightenment cannot initialize EIO!\n"));
461 _e_main_shutdown(-1);
464 _e_main_shutdown_push(eio_shutdown);
466 ecore_app_args_set(argc, (const char **)argv);
468 TS("Ecore Event Handlers");
469 if (!ecore_event_handler_add(ECORE_EVENT_SIGNAL_EXIT,
470 _e_main_cb_signal_exit, NULL))
472 e_error_message_show(_("Enlightenment cannot set up an exit signal handler.\n"
473 "Perhaps you are out of memory?"));
474 _e_main_shutdown(-1);
476 if (!ecore_event_handler_add(ECORE_EVENT_SIGNAL_HUP,
477 _e_main_cb_signal_hup, NULL))
479 e_error_message_show(_("Enlightenment cannot set up a HUP signal handler.\n"
480 "Perhaps you are out of memory?"));
481 _e_main_shutdown(-1);
483 if (!ecore_event_handler_add(ECORE_EVENT_SIGNAL_USER,
484 _e_main_cb_signal_user, NULL))
486 e_error_message_show(_("Enlightenment cannot set up a USER signal handler.\n"
487 "Perhaps you are out of memory?"));
488 _e_main_shutdown(-1);
490 TS("Ecore Event Handlers Done");
492 TS("Ecore_File Init");
493 if (!ecore_file_init())
495 e_error_message_show(_("Enlightenment cannot initialize Ecore_File!\n"));
496 _e_main_shutdown(-1);
498 TS("Ecore_File Init Done");
499 _e_main_shutdown_push(ecore_file_shutdown);
501 _idle_before = ecore_idle_enterer_before_add(_e_main_cb_idle_before, NULL);
503 TS("XDG_DATA_DIRS Init");
504 _xdg_data_dirs_augment();
505 TS("XDG_DATA_DIRS Init Done");
507 TS("Ecore_Evas Init");
508 if (!ecore_evas_init())
510 e_error_message_show(_("Enlightenment cannot initialize Ecore_Evas!\n"));
511 _e_main_shutdown(-1);
513 TS("Ecore_Evas Init Done");
515 /* e doesn't sync to compositor - it should be one */
516 ecore_evas_app_comp_sync_set(0);
521 e_error_message_show(_("Enlightenment cannot initialize Edje!\n"));
522 _e_main_shutdown(-1);
524 TS("Edje Init Done");
525 _e_main_shutdown_push(edje_shutdown);
527 /*** Initialize E Subsystems We Need ***/
529 TS("E Directories Init");
530 /* setup directories we will be using for configurations storage etc. */
531 if (!_e_main_dirs_init())
533 e_error_message_show(_("Enlightenment cannot create directories in your home directory.\n"
534 "Perhaps you have no home directory or the disk is full?"));
535 _e_main_shutdown(-1);
537 TS("E Directories Init Done");
538 _e_main_shutdown_push(_e_main_dirs_shutdown);
541 if (!e_config_init())
543 e_error_message_show(_("Enlightenment cannot set up its config system.\n"));
544 _e_main_shutdown(-1);
546 TS("E_Config Init Done");
547 _e_main_shutdown_push(e_config_shutdown);
552 e_error_message_show(_("Enlightenment cannot set up its environment.\n"));
553 _e_main_shutdown(-1);
555 TS("E_Env Init Done");
556 _e_main_shutdown_push(e_env_shutdown);
558 ecore_exe_run_priority_set(e_config->priority);
561 if (!_e_main_path_init())
563 e_error_message_show(_("Enlightenment cannot set up paths for finding files.\n"
564 "Perhaps you are out of memory?"));
565 _e_main_shutdown(-1);
567 TS("E Paths Init Done");
568 _e_main_shutdown_push(_e_main_path_shutdown);
570 ecore_animator_frametime_set(1.0 / e_config->framerate);
575 e_error_message_show(_("Enlightenment cannot set up its theme system.\n"));
576 _e_main_shutdown(-1);
578 TS("E_Theme Init Done");
579 _e_main_shutdown_push(e_theme_shutdown);
581 TS("E_Actions Init");
582 if (!e_actions_init())
584 e_error_message_show(_("Enlightenment cannot set up its actions system.\n"));
585 _e_main_shutdown(-1);
587 TS("E_Actions Init Done");
588 _e_main_shutdown_push(e_actions_shutdown);
590 /* these just add event handlers and can't fail
591 * timestamping them is dumb.
593 e_screensaver_preinit();
598 TRACE_DS_BEGIN(MAIN:WAIT /dev/dri/card0);
599 if (e_config->sleep_for_dri)
601 while(access("/dev/dri/card0", F_OK) != 0)
603 struct timespec req, rem;
605 req.tv_nsec = 50000000L;
606 nanosleep(&req, &rem);
611 TS("E_Pointer Init");
612 if (!e_pointer_init())
614 e_error_message_show(_("Enlightenment cannot set up its pointer system.\n"));
615 _e_main_shutdown(-1);
617 TS("E_Pointer Init Done");
618 _e_main_shutdown_push(e_pointer_shutdown);
620 TRACE_DS_BEGIN(MAIN:SCREEN INIT);
622 if (!_e_main_screens_init())
624 e_error_message_show(_("Enlightenment set up window management for all the screens on your system\n"
625 "failed. Perhaps another window manager is running?\n"));
626 _e_main_shutdown(-1);
628 TS("Screens Init Done");
629 _e_main_shutdown_push(_e_main_screens_shutdown);
632 if (e_config->eom_enable)
637 e_error_message_show(_("Enlightenment cannot set up eom.\n"));
638 _e_main_shutdown(-1);
641 _e_main_shutdown_push(e_eom_shutdown);
644 TS("E_Screensaver Init");
645 if (!e_screensaver_init())
647 e_error_message_show(_("Enlightenment cannot configure the X screensaver.\n"));
648 _e_main_shutdown(-1);
650 TS("E_Screensaver Init Done");
651 _e_main_shutdown_push(e_screensaver_shutdown);
655 TS("E_Comp Freeze Done");
657 TS("E_Grabinput Init");
658 if (!e_grabinput_init())
660 e_error_message_show(_("Enlightenment cannot set up its grab input handling system.\n"));
661 _e_main_shutdown(-1);
663 TS("E_Grabinput Init Done");
664 _e_main_shutdown_push(e_grabinput_shutdown);
666 TS("E_Gesture Init");
668 _e_main_shutdown_push(e_gesture_shutdown);
670 ecore_event_handler_add(E_EVENT_MODULE_INIT_END, _e_main_deferred_job_schedule, NULL);
673 if (!e_module_init())
675 e_error_message_show(_("Enlightenment cannot set up its module system.\n"));
676 _e_main_shutdown(-1);
678 TS("E_Module Init Done");
679 _e_main_shutdown_push(e_module_shutdown);
682 if (!e_mouse_update())
684 e_error_message_show(_("Enlightenment cannot configure the mouse settings.\n"));
685 _e_main_shutdown(-1);
687 TS("E_Mouse Init Done");
692 e_error_message_show(_("Enlightenment cannot initialize the Icon Cache system.\n"));
693 _e_main_shutdown(-1);
695 TS("E_Icon Init Done");
696 _e_main_shutdown_push(e_icon_shutdown);
698 if (e_config->use_e_policy)
701 if (!e_policy_init())
703 e_error_message_show(_("Enlightenment cannot setup policy system!\n"));
704 _e_main_shutdown(-1);
706 TS("E_Policy Init Done");
707 _e_main_shutdown_push(e_policy_shutdown);
710 TS("E_Process Init");
711 if (!e_process_init())
713 e_error_message_show(_("Enlightenment cannot setup process managing system!\n"));
714 _e_main_shutdown(-1);
716 TS("E_Process Init Done");
717 _e_main_shutdown_push(e_process_shutdown);
719 TS("E_Security Init");
720 if (!e_security_init())
722 e_error_message_show(_("Enlightenment cannot setup security system!\n"));
723 _e_main_shutdown(-1);
725 TS("E_Security Init Done");
726 _e_main_shutdown_push(e_security_shutdown);
729 _e_main_modules_load(safe_mode);
730 TS("Load Modules Done");
734 TS("E_Comp Thaw Done");
736 _idle_after = ecore_idle_enterer_add(_e_main_cb_idle_after, NULL);
738 starting = EINA_FALSE;
741 e_util_env_set("E_RESTART", "1");
743 TS("MAIN LOOP AT LAST");
745 if (e_config->create_wm_ready)
746 _e_main_create_wm_ready();
751 TS("[WM] Send start-up completion");
752 sd_notify(0, "READY=1");
754 TS("[WM] Skip sending start-up completion. (no systemd)");
756 ecore_main_loop_begin();
760 ELOGF("COMP", "STOPPING enlightenment...", NULL, NULL);
761 stopping = EINA_TRUE;
764 e_comp_internal_save();
770 e_util_env_set("E_RESTART_OK", "1");
771 if (getenv("E_START_MTRACK"))
772 e_util_env_set("MTRACK", "track");
782 e_main_ts(const char *str)
785 t1 = ecore_time_unix_get();
786 printf("ESTART: %1.5f [%1.5f] - %s\n", t1 - t0, t1 - t2, str);
792 /* local functions */
794 _e_main_shutdown(int errcode)
800 printf("E: Begin Shutdown Procedure!\n");
802 E_FREE_LIST(hooks, e_main_hook_del);
804 if (_idle_before) ecore_idle_enterer_del(_idle_before);
806 if (_idle_after) ecore_idle_enterer_del(_idle_after);
809 dir = getenv("XDG_RUNTIME_DIR");
812 char buf_env[PATH_MAX];
813 snprintf(buf_env, sizeof(buf_env), "%s", dir);
814 snprintf(buf, sizeof(buf), "%s/.e-deleteme", buf_env);
815 if (ecore_file_exists(buf)) ecore_file_recursive_rm(buf_env);
817 for (i = (_e_main_lvl - 1); i >= 0; i--)
818 (*_e_main_shutdown_func[i])();
819 #ifdef OBJECT_HASH_CHECK
820 e_object_hash_shutdown();
822 if (errcode < 0) exit(errcode);
826 _e_main_shutdown_push(int (*func)(void))
829 if (_e_main_lvl > MAX_LEVEL)
832 e_error_message_show("WARNING: too many init levels. MAX = %i\n",
836 _e_main_shutdown_func[_e_main_lvl - 1] = func;
840 _e_main_parse_arguments(int argc, char **argv)
844 /* handle some command-line parameters */
845 for (i = 1; i < argc; i++)
847 if (!strcmp(argv[i], "-good"))
851 printf("LA LA LA\n");
853 else if (!strcmp(argv[i], "-evil"))
857 printf("MUHAHAHAHHAHAHAHAHA\n");
859 else if (!strcmp(argv[i], "-psychotic"))
863 printf("MUHAHALALALALALALALA\n");
865 else if ((!strcmp(argv[i], "-profile")) && (i < (argc - 1)))
868 if (!getenv("E_CONF_PROFILE"))
869 e_util_env_set("E_CONF_PROFILE", argv[i]);
871 else if (!strcmp(argv[i], "-i-really-know-what-i-am-doing-and-accept-full-responsibility-for-it"))
872 really_know = EINA_TRUE;
873 else if (!strcmp(argv[i], "-nopause"))
874 e_nopause = EINA_TRUE;
875 else if ((!strcmp(argv[i], "-version")) ||
876 (!strcmp(argv[i], "--version")))
878 printf(_("Version: %s\n"), PACKAGE_VERSION);
879 _e_main_shutdown(-1);
881 else if ((!strcmp(argv[i], "-h")) ||
882 (!strcmp(argv[i], "-help")) ||
883 (!strcmp(argv[i], "--help")))
888 "\t-display DISPLAY\n"
889 "\t\tConnect to display named DISPLAY.\n"
890 "\t\tEG: -display :1.0\n"
891 "\t-fake-xinerama-screen WxH+X+Y\n"
892 "\t\tAdd a FAKE xinerama screen (instead of the real ones)\n"
893 "\t\tgiven the geometry. Add as many as you like. They all\n"
894 "\t\treplace the real xinerama screens, if any. This can\n"
895 "\t\tbe used to simulate xinerama.\n"
896 "\t\tEG: -fake-xinerama-screen 800x600+0+0 -fake-xinerama-screen 800x600+800+0\n"
897 "\t-profile CONF_PROFILE\n"
898 "\t\tUse the configuration profile CONF_PROFILE instead of the user selected default or just \"default\".\n"
904 "\t\tBe psychotic.\n"
905 "\t-i-really-know-what-i-am-doing-and-accept-full-responsibility-for-it\n"
906 "\t\tIf you need this help, you don't need this option.\n"
910 _e_main_shutdown(-1);
916 _e_main_cb_signal_exit(void *data EINA_UNUSED, int ev_type EINA_UNUSED, void *ev EINA_UNUSED)
918 /* called on ctrl-c, kill (pid) (also SIGINT, SIGTERM and SIGQIT) */
919 ecore_main_loop_quit();
920 return ECORE_CALLBACK_RENEW;
924 _e_main_cb_signal_hup(void *data EINA_UNUSED, int ev_type EINA_UNUSED, void *ev EINA_UNUSED)
927 ecore_main_loop_quit();
928 return ECORE_CALLBACK_RENEW;
932 _e_main_cb_signal_user(void *data EINA_UNUSED, int ev_type EINA_UNUSED, void *ev)
934 Ecore_Event_Signal_User *e = ev;
938 // E_Action *a = e_action_find("configuration");
939 // if ((a) && (a->func.go)) a->func.go(NULL, NULL);
941 else if (e->number == 2)
943 // comp module has its own handler for this for enabling/disabling fps debug
945 return ECORE_CALLBACK_RENEW;
950 _e_main_dirs_init(void)
952 if(getenv("E_CONF_RO"))
966 base = e_user_dir_get();
967 if (ecore_file_mksubdirs(base, dirs) != sizeof(dirs) / sizeof(dirs[0]) - 1)
969 e_error_message_show("Could not create one of the required "
970 "subdirectories of '%s'\n", base);
978 _e_main_dirs_shutdown(void)
984 _e_main_path_init(void)
988 /* setup data paths */
989 path_data = e_path_new();
992 e_error_message_show("Cannot allocate path for path_data\n");
995 e_prefix_data_concat_static(buf, "data");
996 e_path_default_path_append(path_data, buf);
998 /* setup image paths */
999 path_images = e_path_new();
1002 e_error_message_show("Cannot allocate path for path_images\n");
1005 e_user_dir_concat_static(buf, "/images");
1006 e_path_default_path_append(path_images, buf);
1007 e_prefix_data_concat_static(buf, "data/images");
1008 e_path_default_path_append(path_images, buf);
1010 /* setup font paths */
1011 path_fonts = e_path_new();
1014 e_error_message_show("Cannot allocate path for path_fonts\n");
1017 e_user_dir_concat_static(buf, "/fonts");
1018 e_path_default_path_append(path_fonts, buf);
1019 e_prefix_data_concat_static(buf, "data/fonts");
1020 e_path_default_path_append(path_fonts, buf);
1022 /* setup icon paths */
1023 path_icons = e_path_new();
1026 e_error_message_show("Cannot allocate path for path_icons\n");
1029 e_user_dir_concat_static(buf, "/icons");
1030 e_path_default_path_append(path_icons, buf);
1031 e_prefix_data_concat_static(buf, "data/icons");
1032 e_path_default_path_append(path_icons, buf);
1034 /* setup module paths */
1035 path_modules = e_path_new();
1038 e_error_message_show("Cannot allocate path for path_modules\n");
1041 e_user_dir_concat_static(buf, "/modules");
1042 e_path_default_path_append(path_modules, buf);
1043 snprintf(buf, sizeof(buf), "%s/enlightenment/modules", e_prefix_lib_get());
1044 e_path_default_path_append(path_modules, buf);
1045 /* FIXME: eventually this has to go - moduels should have installers that
1046 * add appropriate install paths (if not installed to user homedir) to
1047 * e's module search dirs
1049 snprintf(buf, sizeof(buf), "%s/enlightenment/modules_extra", e_prefix_lib_get());
1050 e_path_default_path_append(path_modules, buf);
1052 /* setup background paths */
1053 path_backgrounds = e_path_new();
1054 if (!path_backgrounds)
1056 e_error_message_show("Cannot allocate path for path_backgrounds\n");
1059 e_user_dir_concat_static(buf, "/backgrounds");
1060 e_path_default_path_append(path_backgrounds, buf);
1061 e_prefix_data_concat_static(buf, "data/backgrounds");
1062 e_path_default_path_append(path_backgrounds, buf);
1064 path_messages = e_path_new();
1067 e_error_message_show("Cannot allocate path for path_messages\n");
1070 e_user_dir_concat_static(buf, "/locale");
1071 e_path_default_path_append(path_messages, buf);
1072 e_path_default_path_append(path_messages, e_prefix_locale_get());
1078 _e_main_path_shutdown(void)
1082 e_object_del(E_OBJECT(path_data));
1087 e_object_del(E_OBJECT(path_images));
1092 e_object_del(E_OBJECT(path_fonts));
1097 e_object_del(E_OBJECT(path_icons));
1102 e_object_del(E_OBJECT(path_modules));
1103 path_modules = NULL;
1105 if (path_backgrounds)
1107 e_object_del(E_OBJECT(path_backgrounds));
1108 path_backgrounds = NULL;
1112 e_object_del(E_OBJECT(path_messages));
1113 path_messages = NULL;
1119 _e_main_screens_init(void)
1121 TS("\tscreens: client");
1122 if (!e_client_init()) return 0;
1124 TS("Compositor Init");
1125 PRCTL("[Winsys] start of compositor init");
1128 e_error_message_show(_("Enlightenment cannot create a compositor.\n"));
1129 _e_main_shutdown(-1);
1132 PRCTL("[Winsys] end of compositor init");
1133 _e_main_desk_restore();
1139 _e_main_screens_shutdown(void)
1143 e_client_shutdown();
1152 _e_main_desk_save(void)
1155 char env[1024], name[1024];
1158 EINA_LIST_FOREACH(e_comp->zones, l, zone)
1160 snprintf(name, sizeof(name), "DESK_%d_%d", 0, zone->num);
1161 snprintf(env, sizeof(env), "%d,%d", zone->desk_x_current, zone->desk_y_current);
1162 e_util_env_set(name, env);
1167 _e_main_desk_restore(void)
1171 E_CLIENT_REVERSE_FOREACH(ec)
1172 if ((!e_client_util_ignored_get(ec)) && e_client_util_desk_visible(ec, e_desk_current_get(ec->zone)))
1174 ec->want_focus = ec->take_focus = 1;
1180 _e_main_modules_load_after(void *d EINA_UNUSED, int type EINA_UNUSED, void *ev EINA_UNUSED)
1182 E_FREE_FUNC(mod_init_end, ecore_event_handler_del);
1183 return ECORE_CALLBACK_RENEW;
1187 _e_main_modules_load(Eina_Bool safe_mode)
1190 e_module_all_load();
1196 crashmodule = getenv("E_MODULE_LOAD");
1197 if (crashmodule) m = e_module_new(crashmodule);
1199 if ((crashmodule) && (m))
1201 e_module_disable(m);
1202 e_object_del(E_OBJECT(m));
1204 e_error_message_show
1205 (_("Enlightenment crashed early on start and has<br>"
1206 "been restarted. There was an error loading the<br>"
1207 "module named: %s. This module has been disabled<br>"
1208 "and will not be loaded."), crashmodule);
1210 (_("Enlightenment crashed early on start and has been restarted"),
1211 _("Enlightenment crashed early on start and has been restarted.<br>"
1212 "There was an error loading the module named: %s<br><br>"
1213 "This module has been disabled and will not be loaded."), crashmodule);
1214 e_module_all_load();
1218 e_error_message_show
1219 (_("Enlightenment crashed early on start and has<br>"
1220 "been restarted. All modules have been disabled<br>"
1221 "and will not be loaded to help remove any problem<br>"
1222 "modules from your configuration. The module<br>"
1223 "configuration dialog should let you select your<br>"
1224 "modules again.\n"));
1226 (_("Enlightenment crashed early on start and has been restarted"),
1227 _("Enlightenment crashed early on start and has been restarted.<br>"
1228 "All modules have been disabled and will not be loaded to help<br>"
1229 "remove any problem modules from your configuration.<br><br>"
1230 "The module configuration dialog should let you select your<br>"
1233 mod_init_end = ecore_event_handler_add(E_EVENT_MODULE_INIT_END, _e_main_modules_load_after, NULL);
1238 _e_main_cb_idle_before(void *data EINA_UNUSED)
1240 e_client_idler_before();
1242 return ECORE_CALLBACK_RENEW;
1246 _e_main_cb_idle_after(void *data EINA_UNUSED)
1248 static int first_idle = 1;
1253 #ifdef E_RELEASE_BUILD
1258 e_precache_end = EINA_TRUE;
1261 if (first_idle++ < 60)
1265 e_precache_end = EINA_TRUE;
1269 return ECORE_CALLBACK_RENEW;
1273 _e_main_create_wm_ready(void)
1275 FILE *_wmready_checker = NULL;
1276 const char *path_wm_ready = "/run/.wm_ready";
1278 if (!e_util_file_realpath_check(path_wm_ready, EINA_TRUE))
1280 WRN("%s is maybe link, so delete it\n", path_wm_ready);
1283 _wmready_checker = fopen(path_wm_ready, "wb");
1284 if (_wmready_checker)
1286 TS("[WM] WINDOW MANAGER is READY!!!");
1287 PRCTL("[Winsys] WINDOW MANAGER is READY!!!");
1288 fclose(_wmready_checker);
1290 /*TODO: Next lines should be removed. */
1291 FILE *_tmp_wm_ready_checker;
1293 _tmp_wm_ready_checker = fopen(path_wm_ready, "wb");
1295 if (_tmp_wm_ready_checker)
1297 TS("[WM] temporary wm_ready path is created.");
1298 PRCTL("[Winsys] temporary wm_ready path is created.");
1299 fclose(_tmp_wm_ready_checker);
1303 TS("[WM] temporary wm_ready path create failed.");
1304 PRCTL("[Winsys] temporary wm_ready path create failed.");
1309 TS("[WM] WINDOW MANAGER is READY. BUT, failed to create .wm_ready file.");
1310 PRCTL("[Winsys] WINDOW MANAGER is READY. BUT, failed to create .wm_ready file.");
1315 _e_main_hooks_clean(void)
1321 for (x = 0; x < E_MAIN_HOOK_LAST; x++)
1322 EINA_INLIST_FOREACH_SAFE(_e_main_hooks[x], l, mh)
1324 if (!mh->delete_me) continue;
1325 _e_main_hooks[x] = eina_inlist_remove(_e_main_hooks[x],
1326 EINA_INLIST_GET(mh));
1332 _e_main_hook_call(E_Main_Hook_Point hookpoint, void *data EINA_UNUSED)
1336 _e_main_hooks_walking++;
1337 EINA_INLIST_FOREACH(_e_main_hooks[hookpoint], mh)
1339 if (mh->delete_me) continue;
1342 _e_main_hooks_walking--;
1343 if ((_e_main_hooks_walking == 0) && (_e_main_hooks_delete > 0))
1344 _e_main_hooks_clean();
1348 e_main_hook_add(E_Main_Hook_Point hookpoint, E_Main_Hook_Cb func, const void *data)
1352 EINA_SAFETY_ON_TRUE_RETURN_VAL(hookpoint >= E_MAIN_HOOK_LAST, NULL);
1353 mh = E_NEW(E_Main_Hook, 1);
1354 EINA_SAFETY_ON_NULL_RETURN_VAL(mh, NULL);
1355 mh->hookpoint = hookpoint;
1357 mh->data = (void*)data;
1358 _e_main_hooks[hookpoint] = eina_inlist_append(_e_main_hooks[hookpoint],
1359 EINA_INLIST_GET(mh));
1364 e_main_hook_del(E_Main_Hook *mh)
1367 if (_e_main_hooks_walking == 0)
1369 _e_main_hooks[mh->hookpoint] = eina_inlist_remove(_e_main_hooks[mh->hookpoint],
1370 EINA_INLIST_GET(mh));
1374 _e_main_hooks_delete++;
1378 e_main_hook_call(E_Main_Hook_Point hookpoint)
1380 if ((hookpoint < 0) || (hookpoint >= E_MAIN_HOOK_LAST)) return;
1382 _e_main_hook_call(hookpoint, NULL);