8795dc30a82052c4ba1a3aa241288a162484e5c5
[framework/uifw/e17.git] / src / preload / e_precache.c
1 #include "config.h"
2 #include "e_precache.h"
3
4 static void *lib_evas = NULL;
5 static void *lib_ecore_file = NULL;
6 static void *lib_eet = NULL;
7
8 static int *e_precache_end = NULL;
9
10 /* internal calls */
11 static int log_fd = -1;
12 static int do_log = 0;
13
14 static void
15 log_open(void)
16 {
17    char buf[4096] = "DUMMY", *home;
18    
19    if (log_fd != -1) return;
20    if (!e_precache_end)
21      {
22 #ifdef HAVE_UNSETENV
23         unsetenv("LD_PRELOAD");
24 #else
25         if (getenv("LD_PRELOAD")) putenv("LD_PRELOAD");
26 #endif
27         e_precache_end = dlsym(NULL, "e_precache_end");
28      }
29    if (!e_precache_end) return;
30    if (*e_precache_end) return;
31    
32    home = getenv("HOME");
33    if (home)
34      snprintf(buf, sizeof(buf), "%s/.e-precache", home);
35    else
36      snprintf(buf, sizeof(buf), "/tmp/.e-precache");
37    log_fd = open(buf, O_CREAT | O_TRUNC | O_WRONLY, S_IRUSR | S_IWUSR);
38    if (log_fd) do_log = 1;
39 }
40
41 static void
42 log_close(void)
43 {
44    if (log_fd >= 0)
45      {
46         close(log_fd);
47         log_fd = -1;
48      }
49    do_log = 0;
50 }
51
52 static void
53 log_write(const char *type, const char *file)
54 {
55    static Eina_Hash *s_hash = NULL;
56    static Eina_Hash *o_hash = NULL;
57    static Eina_Hash *d_hash = NULL;
58    char buf[2];
59
60    if ((e_precache_end) && (*e_precache_end))
61      {
62         log_close();
63         return;
64      }
65    if (type[0] == 's')
66      {
67         if (eina_hash_find(s_hash, file)) return;
68         if (!s_hash) s_hash = eina_hash_string_superfast_new(NULL);
69         eina_hash_add(s_hash, file, (void *)1);
70      }
71    else if (type[0] == 'o')
72      {
73         if (eina_hash_find(o_hash, file)) return;
74         if (!o_hash) o_hash = eina_hash_string_superfast_new(NULL);
75         eina_hash_add(o_hash, file, (void *)1);
76      }
77    else if (type[0] == 'd')
78      {
79         if (eina_hash_find(d_hash, file)) return;
80         if (!d_hash) d_hash = eina_hash_string_superfast_new(NULL);
81         eina_hash_add(d_hash, file, (void *)1);
82      }
83    buf[0] = type[0]; buf[1] = ' ';
84    write(log_fd, buf, 2);
85    write(log_fd, file, strlen(file));
86    write(log_fd, "\n", 1);
87 }
88
89 static void *
90 lib_func(const char *lib1, const char *lib2, const char *fname, const char *libname, void **lib)
91 {
92    void *func;
93    
94    if (!*lib) *lib = dlopen(lib1, RTLD_GLOBAL | RTLD_LAZY);
95    if (!*lib) *lib = dlopen(lib2, RTLD_GLOBAL | RTLD_LAZY);
96    func = dlsym(*lib, fname);
97    if (!func)
98      {
99         printf("ABORT: Can't find %s() in %s or %s (%s = %p)\n",
100                fname, lib1, lib2, libname, *lib);
101         abort();
102      }
103    log_open();
104    return func;
105 }
106
107 /* intercepts */
108 void
109 evas_object_image_file_set(Evas_Object *obj, const char *file, const char *key)
110 {
111    static void (*func) (Evas_Object *obj, const char *file, const char *key) = NULL;
112    if (!func)
113      func = lib_func("libevas.so", "libevas.so.1", 
114                      "evas_object_image_file_set", "lib_evas", &lib_evas);
115    if (do_log) log_write("o", file);
116    (*func) (obj, file, key);
117 }
118
119 long long
120 ecore_file_mod_time(const char *file)
121 {
122    static long long (*func) (const char *file) = NULL;
123    if (!func)
124      func = lib_func("libecore_file.so", "libecore_file.so.1", 
125                      "ecore_file_mod_time", "lib_ecore_file", &lib_ecore_file);
126    if (do_log) log_write("s", file);
127    return (*func) (file);
128 }
129
130 long long
131 ecore_file_size(const char *file)
132 {
133    static int (*func) (const char *file) = NULL;
134    if (!func)
135      func = lib_func("libecore_file.so", "libecore_file.so.1", 
136                      "ecore_file_size", "lib_ecore_file", &lib_ecore_file);
137    if (do_log) log_write("s", file);
138    return (*func) (file);
139 }
140
141 Eina_Bool
142 ecore_file_exists(const char *file)
143 {
144    static int (*func) (const char *file) = NULL;
145    if (!func)
146      func = lib_func("libecore_file.so", "libecore_file.so.1", 
147                      "ecore_file_exists", "lib_ecore_file", &lib_ecore_file);
148    if (do_log) log_write("s", file);
149    return (*func) (file);
150 }
151
152 Eina_Bool
153 ecore_file_is_dir(const char *file)
154 {
155    static int (*func) (const char *file) = NULL;
156    if (!func)
157      func = lib_func("libecore_file.so", "libecore_file.so.1", 
158                      "ecore_file_is_dir", "lib_ecore_file", &lib_ecore_file);
159    if (do_log) log_write("s", file);
160    return (*func) (file);
161 }
162
163 Eina_Bool
164 ecore_file_can_read(const char *file)
165 {
166    static int (*func) (const char *file) = NULL;
167    if (!func)
168      func = lib_func("libecore_file.so", "libecore_file.so.1", 
169                      "ecore_file_can_read", "lib_ecore_file", &lib_ecore_file);
170    if (do_log) log_write("s", file);
171    return (*func) (file);
172 }
173
174 Eina_Bool
175 ecore_file_can_write(const char *file)
176 {
177    static int (*func) (const char *file) = NULL;
178    if (!func)
179      func = lib_func("libecore_file.so", "libecore_file.so.1", 
180                      "ecore_file_can_write", "lib_ecore_file", &lib_ecore_file);
181    if (do_log) log_write("s", file);
182    return (*func) (file);
183 }
184
185 Eina_Bool
186 ecore_file_can_exec(const char *file)
187 {
188    static int (*func) (const char *file) = NULL;
189    if (!func)
190      func = lib_func("libecore_file.so", "libecore_file.so.1", 
191                      "ecore_file_can_exec", "lib_ecore_file", &lib_ecore_file);
192    if (do_log) log_write("s", file);
193    return (*func) (file);
194 }
195
196 Eina_List *
197 ecore_file_ls(const char *file)
198 {
199    static Eina_List * (*func) (const char *file) = NULL;
200    if (!func)
201      func = lib_func("libecore_file.so", "libecore_file.so.1", 
202                      "ecore_file_ls", "lib_ecore_file", &lib_ecore_file);
203    if (do_log) log_write("d", file);
204    return (*func) (file);
205 }
206
207 Eet_File *
208 eet_open(const char *file, Eet_File_Mode mode)
209 {
210    static Eet_File * (*func) (const char *file, Eet_File_Mode mode) = NULL;
211    if (!func)
212      func = lib_func("libeet.so", "libeet.so.0", 
213                      "eet_open", "lib_eet", &lib_eet);
214    if (do_log) log_write("o", file);
215    return (*func) (file, mode);
216 }