Tizen 2.1 base
[framework/uifw/ecore.git] / src / lib / ecore_file / ecore_file.c
1 #ifdef HAVE_CONFIG_H
2 # include <config.h>
3 #endif
4
5 #include <stdlib.h>
6 #include <stdio.h>
7 #include <string.h>
8
9 #ifndef _MSC_VER
10 # include <unistd.h>
11 # include <libgen.h>
12 #endif
13
14 #ifdef _WIN32
15 # include <direct.h>
16 #endif
17
18 #ifdef HAVE_FEATURES_H
19 # include <features.h>
20 #endif
21 #include <ctype.h>
22 #include <errno.h>
23
24 #ifdef HAVE_ATFILE_SOURCE
25 # include <dirent.h>
26 #endif
27
28 #include "ecore_file_private.h"
29
30 int _ecore_file_log_dom = -1;
31 static int _ecore_file_init_count = 0;
32
33 /* externally accessible functions */
34
35 /**
36  * @addtogroup Ecore_File_Group Ecore_File - Files and directories convenience functions
37  *
38  * @{
39  */
40
41 /**
42  * @brief Initialize the Ecore_File library.
43  *
44  * @return 1 or greater on success, 0 on error.
45  *
46  * This function sets up Ecore_File and the services it will use
47  * (monitoring, downloading, PATH related feature). It returns 0 on
48  * failure, otherwise it returns the number of times it has already
49  * been called.
50  *
51  * When Ecore_File is not used anymore, call ecore_file_shutdown()
52  * to shut down the Ecore_File library.
53  */
54 EAPI int
55 ecore_file_init()
56 {
57    if (++_ecore_file_init_count != 1)
58      return _ecore_file_init_count;
59
60    if (!ecore_init())
61      return --_ecore_file_init_count;
62
63    _ecore_file_log_dom = eina_log_domain_register
64      ("ecore_file", ECORE_FILE_DEFAULT_LOG_COLOR);
65    if(_ecore_file_log_dom < 0)
66      {
67        EINA_LOG_ERR("Impossible to create a log domain for the ecore file module.");
68        return --_ecore_file_init_count;
69      }
70    ecore_file_path_init();
71    ecore_file_monitor_init();
72    ecore_file_download_init();
73
74    /* FIXME: were the tests disabled for a good reason ? */
75
76    /*
77    if (!ecore_file_monitor_init())
78      goto shutdown_ecore_file_path;
79
80    if (!ecore_file_download_init())
81      goto shutdown_ecore_file_monitor;
82    */
83
84    return _ecore_file_init_count;
85
86    /*
87  shutdown_ecore_file_monitor:
88    ecore_file_monitor_shutdown();
89  shutdown_ecore_file_path:
90    ecore_file_path_shutdown();
91
92    return --_ecore_file_init_count;
93    */
94 }
95
96 /**
97  * @brief Shut down the Ecore_File library.
98  *
99  * @return 0 when the library is completely shut down, 1 or
100  * greater otherwise.
101  *
102  * This function shuts down the Ecore_File library. It returns 0 when it has
103  * been called the same number of times than ecore_file_init(). In that case
104  * it shuts down all the services it uses.
105  */
106 EAPI int
107 ecore_file_shutdown()
108 {
109    if (--_ecore_file_init_count != 0)
110      return _ecore_file_init_count;
111
112    ecore_file_download_shutdown();
113    ecore_file_monitor_shutdown();
114    ecore_file_path_shutdown();
115
116    eina_log_domain_unregister(_ecore_file_log_dom);
117    _ecore_file_log_dom = -1;
118
119    ecore_shutdown();
120
121    return _ecore_file_init_count;
122 }
123
124 /**
125  * @brief Get the time of the last modification to the given file.
126  *
127  * @param file The name of the file.
128  * @return Return the time of the last data modification, or 0 on
129  * failure.
130  *
131  * This function returns the time of the last modification of
132  * @p file. On failure, it returns 0.
133  */
134 EAPI long long
135 ecore_file_mod_time(const char *file)
136 {
137    struct stat st;
138
139    if (stat(file, &st) < 0) return 0;
140    return st.st_mtime;
141 }
142
143 /**
144  * @brief Get the size of the given file.
145  *
146  * @param file The name of the file.
147  * @return Return the size of the file in bytes, or 0 on failure.
148  *
149  * This function returns the size of @p file in bytes. On failure, it
150  * returns 0.
151  */
152 EAPI long long
153 ecore_file_size(const char *file)
154 {
155    struct stat st;
156
157    if (stat(file, &st) < 0) return 0;
158    return st.st_size;
159 }
160
161 /**
162  * @brief Check if the given file exists.
163  *
164  * @param file The name of the file.
165  * @return @c EINA_TRUE if the @p file exists, @c EINA_FALSE otherwise.
166  *
167  * This function returns @c EINA_TRUE if @p file exists on local filesystem,
168  * @c EINA_FALSE otherwise.
169  */
170 EAPI Eina_Bool
171 ecore_file_exists(const char *file)
172 {
173    struct stat st;
174    if (!file) return EINA_FALSE;
175
176    /*Workaround so that "/" returns a true, otherwise we can't monitor "/" in ecore_file_monitor*/
177    if (stat(file, &st) < 0 && strcmp(file, "/")) return EINA_FALSE;
178    return EINA_TRUE;
179 }
180
181 /**
182  * @brief Check if the given file is a directory.
183  *
184  * @param file The name of the file.
185  * @return @c EINA_TRUE if the file exists and is a directory, @c EINA_FALSE
186  * otherwise.
187  *
188  * This function returns @c EINA_TRUE if @p file exists exists and is a
189  * directory on local filesystem, @c EINA_FALSE otherwise.
190  */
191 EAPI Eina_Bool
192 ecore_file_is_dir(const char *file)
193 {
194    struct stat st;
195
196    if (stat(file, &st) < 0) return EINA_FALSE;
197    if (S_ISDIR(st.st_mode)) return EINA_TRUE;
198    return EINA_FALSE;
199 }
200
201 static mode_t default_mode = S_IRUSR | S_IWUSR | S_IXUSR | S_IRGRP | S_IXGRP | S_IROTH | S_IXOTH;
202
203 /**
204  * @brief Create a new directory.
205  *
206  * @param  dir The name of the directory to create
207  * @return @c EINA_TRUE on successful creation, @c EINA_FALSE otherwise.
208  *
209  * This function creates the directory @p dir with the mode S_IRUSR |
210  * S_IWUSR | S_IXUSR | S_IRGRP | S_IXGRP | S_IROTH | S_IXOTH. On
211  * success, it returns @c EINA_TRUE, @c EINA_FALSE otherwise.
212  */
213 EAPI Eina_Bool
214 ecore_file_mkdir(const char *dir)
215 {
216    if (mkdir(dir, default_mode) < 0) return EINA_FALSE;
217    return EINA_TRUE;
218 }
219
220 /**
221  * @brief Create complete directory in a batch.
222  *
223  * @param dirs The list of directories, null terminated.
224  * @return The number of successful directories created, -1 if dirs is
225  * @c NULL.
226  *
227  * This function creates all the directories that are in the null
228  * terminated array @p dirs. The function loops over the directories
229  * and call ecore_file_mkdir(). This function returns -1 if @p dirs is
230  * @c NULL, otherwise if returns the number of suceesfully created
231  * directories.
232  */
233 EAPI int
234 ecore_file_mkdirs(const char **dirs)
235 {
236    int i = 0;
237
238    if (!dirs) return -1;
239
240    for (; *dirs; dirs++)
241      if (ecore_file_mkdir(*dirs))
242        i++;
243    return i;
244 }
245
246 /**
247  * @brief Create complete list of sub-directories in a batch (optimized).
248  *
249  * @param base The base directory to act on.
250  * @param subdirs The list of directories, null terminated.
251  * @return number of successful directories created, -1 on failure.
252  *
253  * This function creates all the directories that are in the null
254  * terminated array @p dirs in the @p base directory. If @p base does
255  * not exist, it will be created. The function loops over the directories
256  * and call ecore_file_mkdir(). The whole path of the directories must
257  * exist. So if base/a/b/c wants to be created, @p subdirs must
258  * contain "a", "a/b" and "a/b/c", in that order. This function
259  * returns -1 if @p dirs or @p base are @c NULL, or if @p base is
260  * empty ("\0"). It returns 0 is @p base is not a directory or
261  * invalid, or if it can't be created. Otherwise if returns the number
262  * of suceesfully created directories.
263  */
264 EAPI int
265 ecore_file_mksubdirs(const char *base, const char **subdirs)
266 {
267 #ifndef HAVE_ATFILE_SOURCE
268    char buf[PATH_MAX];
269    int baselen;
270 #else
271    int fd;
272    DIR *dir;
273 #endif
274    int i;
275
276    if (!subdirs) return -1;
277    if ((!base) || (base[0] == '\0')) return -1;
278
279    if ((!ecore_file_is_dir(base)) && (!ecore_file_mkpath(base)))
280      return 0;
281
282 #ifndef HAVE_ATFILE_SOURCE
283    baselen = eina_strlcpy(buf, base, sizeof(buf));
284    if ((baselen < 1) || (baselen + 1 >= (int)sizeof(buf)))
285      return 0;
286
287    if (buf[baselen - 1] != '/')
288      {
289         buf[baselen] = '/';
290         baselen++;
291      }
292 #else
293    dir = opendir(base);
294    if (!dir)
295      return 0;
296    fd = dirfd(dir);
297 #endif
298
299    i = 0;
300    for (; *subdirs; subdirs++)
301      {
302         struct stat st;
303
304 #ifndef HAVE_ATFILE_SOURCE
305         eina_strlcpy(buf + baselen, *subdirs, sizeof(buf) - baselen);
306         if (stat(buf, &st) == 0)
307 #else
308         if (fstatat(fd, *subdirs, &st, 0) == 0)
309 #endif
310           {
311              if (S_ISDIR(st.st_mode))
312                {
313                   i++;
314                   continue;
315                }
316           }
317         else
318           {
319              if (errno == ENOENT)
320                {
321 #ifndef HAVE_ATFILE_SOURCE
322                   if (mkdir(buf, default_mode) == 0)
323 #else
324                   if (mkdirat(fd, *subdirs, default_mode) == 0)
325 #endif
326                     {
327                        i++;
328                        continue;
329                     }
330                  }
331             }
332      }
333
334 #ifdef HAVE_ATFILE_SOURCE
335    closedir(dir);
336 #endif
337
338    return i;
339 }
340
341 /**
342  * @brief Delete the given directory.
343  *
344  * @param  dir The name of the directory to delete.
345  * @return @c EINA_TRUE on success, @c EINA_FALSE otherwise.
346  *
347  * This function deletes @p dir. It returns @c EINA_TRUE on success,
348  * @c EINA_FALSE otherwise.
349  */
350 EAPI Eina_Bool
351 ecore_file_rmdir(const char *dir)
352 {
353    if (rmdir(dir) < 0) return EINA_FALSE;
354    return EINA_TRUE;
355 }
356
357 /**
358  * @brief Delete the given file.
359  *
360  * @param  file The name of the file to delete.
361  * @return @c EINA_TRUE on success, @c EINA_FALSE otherwise.
362  *
363  * This function deletes @p file. It returns @c EINA_TRUE on success,
364  * @c EINA_FALSE otherwise.
365  */
366 EAPI Eina_Bool
367 ecore_file_unlink(const char *file)
368 {
369    if (unlink(file) < 0) return EINA_FALSE;
370    return EINA_TRUE;
371 }
372
373 /**
374  * @brief Remove the given file or directory.
375  *
376  * @param  file The name of the file or directory to delete.
377  * @return @c EINA_TRUE on success, @c EINA_FALSE otherwise.
378  *
379  * This function removes @p file. It returns @c EINA_TRUE on success,
380  * @c EINA_FALSE otherwise.
381  */
382 EAPI Eina_Bool
383 ecore_file_remove(const char *file)
384 {
385    if (remove(file) < 0) return EINA_FALSE;
386    return EINA_TRUE;
387 }
388
389 /**
390  * @brief Delete the given directory and all its contents.
391  *
392  * @param  dir The name of the directory to delete.
393  * @return @c EINA_TRUE on success, @c EINA_FALSE otherwise.
394  *
395  * This function delete @p dir and all its contents. If @p dir is a
396  * link only the link is removed. It returns @c EINA_TRUE on success,
397  * @c EINA_FALSE otherwise.
398  */
399 EAPI Eina_Bool
400 ecore_file_recursive_rm(const char *dir)
401 {
402    Eina_Iterator *it;
403    char buf[PATH_MAX];
404    struct stat st;
405    int ret;
406
407    if (readlink(dir, buf, sizeof(buf) - 1) > 0)
408      return ecore_file_unlink(dir);
409
410    ret = stat(dir, &st);
411    if ((ret == 0) && (S_ISDIR(st.st_mode)))
412      {
413         Eina_File_Direct_Info *info;
414
415         ret = 1;
416         if (stat(dir, &st) == -1) return EINA_FALSE; /* WOOT: WHY ARE WE CALLING STAT TWO TIMES ??? */
417
418         it = eina_file_direct_ls(dir);
419         EINA_ITERATOR_FOREACH(it, info)
420           {
421              if (!ecore_file_recursive_rm(info->path))
422                ret = 0;
423           }
424         eina_iterator_free(it);
425
426         if (!ecore_file_rmdir(dir)) ret = 0;
427         if (ret)
428             return EINA_TRUE;
429         else
430             return EINA_FALSE;
431      }
432    else
433      {
434         if (ret == -1) return EINA_FALSE;
435         return ecore_file_unlink(dir);
436      }
437 }
438
439 static inline Eina_Bool
440 _ecore_file_mkpath_if_not_exists(const char *path)
441 {
442    struct stat st;
443
444    /* Windows: path like C: or D: etc are valid, but stat() returns an error */
445 #ifdef _WIN32
446    if ((strlen(path) == 2) &&
447        ((path[0] >= 'a' && path[0] <= 'z') ||
448         (path[0] >= 'A' && path[0] <= 'Z')) &&
449        (path[1] == ':'))
450      return EINA_TRUE;
451 #endif
452
453    if (stat(path, &st) < 0)
454      return ecore_file_mkdir(path);
455    else if (!S_ISDIR(st.st_mode))
456      return EINA_FALSE;
457    else
458      return EINA_TRUE;
459 }
460
461 /**
462  * @brief Create a complete path.
463  *
464  * @param  path The path to create
465  * @return @c EINA_TRUE on success, @c EINA_FALSE otherwise.
466  *
467  * This function creates @p path and all the subdirectories it
468  * contains. The separator is '/' or '\'. If @p path exists, this
469  * function returns @c EINA_TRUE immediately. It returns @c EINA_TRUE on
470  * success, @c EINA_FALSE otherwise.
471  */
472 EAPI Eina_Bool
473 ecore_file_mkpath(const char *path)
474 {
475    char ss[PATH_MAX];
476    unsigned int i;
477
478    if (ecore_file_is_dir(path))
479      return EINA_TRUE;
480
481    for (i = 0; path[i] != '\0'; ss[i] = path[i], i++)
482      {
483         if (i == sizeof(ss) - 1) return EINA_FALSE;
484         if (((path[i] == '/') || (path[i] == '\\')) && (i > 0))
485           {
486              ss[i] = '\0';
487              if (!_ecore_file_mkpath_if_not_exists(ss))
488                return EINA_FALSE;
489           }
490      }
491    ss[i] = '\0';
492    return _ecore_file_mkpath_if_not_exists(ss);
493 }
494
495 /**
496  * @brief Create complete paths in a batch.
497  *
498  * @param paths list of paths, null terminated.
499  * @return number of successful paths created, -1 if paths is NULL.
500  *
501  * This function creates all the directories that are in the null
502  * terminated array @p paths. The function loops over the directories
503  * and call ecore_file_mkpath(), hence on Windows, '\' must be
504  * replaced by '/' before calling that function. This function
505  * returns -1 if @p paths is @c NULL. Otherwise if returns the number
506  * of suceesfully created directories.
507  */
508 EAPI int
509 ecore_file_mkpaths(const char **paths)
510 {
511    int i = 0;
512
513    if (!paths) return -1;
514
515    for (; *paths; paths++)
516      if (ecore_file_mkpath(*paths))
517        i++;
518    return i;
519 }
520
521 /**
522  * @brief Copy the given file to the given destination.
523  *
524  * @param  src The name of the source file.
525  * @param  dst The name of the destination file.
526  * @return @c EINA_TRUE on success, @c EINA_FALSE otherwise.
527  *
528  * This function copies @p src to @p dst. If the absolute path name of
529  * @p src and @p dst can not be computed, or if they are equal, or if
530  * the copy fails, the function returns @c EINA_FALSE, otherwise it
531  * returns @c EINA_TRUE.
532  */
533 EAPI Eina_Bool
534 ecore_file_cp(const char *src, const char *dst)
535 {
536    FILE *f1, *f2;
537    char buf[16384];
538    char realpath1[PATH_MAX], realpath2[PATH_MAX];
539    size_t num;
540    Eina_Bool ret = EINA_TRUE;
541
542    if (!realpath(src, realpath1)) return EINA_FALSE;
543    if (realpath(dst, realpath2) && !strcmp(realpath1, realpath2)) return EINA_FALSE;
544
545    f1 = fopen(src, "rb");
546    if (!f1) return EINA_FALSE;
547    f2 = fopen(dst, "wb");
548    if (!f2)
549      {
550         fclose(f1);
551         return EINA_FALSE;
552      }
553    while ((num = fread(buf, 1, sizeof(buf), f1)) > 0)
554      {
555         if (fwrite(buf, 1, num, f2) != num) ret = EINA_FALSE;
556      }
557    fclose(f1);
558    fclose(f2);
559    return ret;
560 }
561
562 /**
563  * @brief Move the given file to the given destination.
564  *
565  * @param  src The name of the source file.
566  * @param  dst The name of the destination file.
567  * @return @c EINA_TRUE on success, @c EINA_FALSE otherwise.
568  *
569  * This function moves @p src to @p dst. It returns @c EINA_TRUE on
570  * success, @c EINA_FALSE otherwise.
571  */
572 EAPI Eina_Bool
573 ecore_file_mv(const char *src, const char *dst)
574 {
575    char buf[PATH_MAX];
576    int fd;
577
578    if (rename(src, dst))
579      {
580         // File cannot be moved directly because
581         // it resides on a different mount point.
582         if (errno == EXDEV)
583           {
584              struct stat st;
585
586              // Make sure this is a regular file before
587              // we do anything fancy.
588              stat(src, &st);
589              if (S_ISREG(st.st_mode))
590                {
591                   char *dir;
592
593                   dir = ecore_file_dir_get(dst);
594                   // Since we can't directly rename, try to
595                   // copy to temp file in the dst directory
596                   // and then rename.
597                   snprintf(buf, sizeof(buf), "%s/.%s.tmp.XXXXXX",
598                            dir, ecore_file_file_get(dst));
599                   free(dir);
600                   fd = mkstemp(buf);
601                   if (fd < 0) goto FAIL;
602                   close(fd);
603
604                   // Copy to temp file
605                   if (!ecore_file_cp(src, buf))
606                     goto FAIL;
607
608                   // Set file permissions of temp file to match src
609                   chmod(buf, st.st_mode);
610
611                   // Try to atomically move temp file to dst
612                   if (rename(buf, dst))
613                     {
614                        // If we still cannot atomically move
615                        // do a normal copy and hope for the best.
616                        if (!ecore_file_cp(buf, dst))
617                          goto FAIL;
618                     }
619
620                   // Delete temporary file and src
621                   ecore_file_unlink(buf);
622                   ecore_file_unlink(src);
623                   goto PASS;
624                }
625           }
626         goto FAIL;
627      }
628
629 PASS:
630    return EINA_TRUE;
631
632 FAIL:
633    return EINA_FALSE;
634 }
635
636 /**
637  * @brief Create a symbolic link.
638  *
639  * @param  src The name of the file to link.
640  * @param  dest The name of link.
641  * @return @c EINA_TRUE on success, @c EINA_FALSE otherwise.
642  *
643  * This function create the symbolic link @p dest of @p src. This
644  * function does not work on Windows. It returns @c EINA_TRUE on success,
645  * @c EINA_FALSE otherwise.
646  */
647 EAPI Eina_Bool
648 ecore_file_symlink(const char *src, const char *dest)
649 {
650    if (!symlink(src, dest)) return EINA_TRUE;
651
652    return EINA_FALSE;
653 }
654
655 /**
656  * @brief Get the canonicalized absolute path name.
657  *
658  * @param  file The file path.
659  * @return The canonicalized absolute pathname or an empty string on
660  * failure.
661  *
662  * This function returns the absolute path name of @p file as a newly
663  * allocated string. If @p file is @c NULL, or on error, this function
664  * returns an empty string. Otherwise, it returns the absolute path
665  * name. When not needed anymore, the returned value must be freed.
666  */
667 EAPI char *
668 ecore_file_realpath(const char *file)
669 {
670    char buf[PATH_MAX];
671
672    /*
673     * Some implementations of realpath do not conform to the SUS.
674     * And as a result we must prevent a null arg from being passed.
675     */
676    if (!file) return strdup("");
677    if (!realpath(file, buf)) return strdup("");
678
679    return strdup(buf);
680 }
681
682 /**
683  * Get the filename from a given path.
684  *
685  * @param  path The complete path.
686  * @return The file name.
687  *
688  * This function returns the file name of @p path. If @p path is
689  * @c NULL, the functions returns @c NULL.
690  */
691 EAPI const char *
692 ecore_file_file_get(const char *path)
693 {
694    char *result = NULL;
695
696    if (!path) return NULL;
697    if ((result = strrchr(path, '/'))) result++;
698    else result = (char *)path;
699    return result;
700 }
701
702 /**
703  * @brief Get the directory where the given file resides.
704  *
705  * @param  file The name of the file.
706  * @return The directory name.
707  *
708  * This function returns the directory where @p file resides as anewly
709  * allocated string. If @p file is @c NULL or on error, this function
710  * returns @c NULL. When not needed anymore, the returned value must
711  * be freed.
712  */
713 EAPI char *
714 ecore_file_dir_get(const char *file)
715 {
716    char *p;
717    char buf[PATH_MAX];
718
719    if (!file) return NULL;
720    strncpy(buf, file, PATH_MAX);
721    buf[PATH_MAX - 1] = 0;
722    p = dirname(buf);
723    return strdup(p);
724 }
725
726 /**
727  * @brief Check if the given file can be read.
728  *
729  * @param  file The name of the file.
730  * @return @c EINA_TRUE if the @p file is readable, @c EINA_FALSE otherwise.
731  *
732  * This function returns @c EINA_TRUE if @p file can be read, @c EINA_FALSE
733  * otherwise.
734  */
735 EAPI Eina_Bool
736 ecore_file_can_read(const char *file)
737 {
738    if (!file) return EINA_FALSE;
739    if (!access(file, R_OK)) return EINA_TRUE;
740    return EINA_FALSE;
741 }
742
743 /**
744  * @brief Check if the given file can be written.
745  *
746  * @param  file The name of the file.
747  * @return @c EINA_TRUE if the @p file is writable, @c EINA_FALSE otherwise.
748  *
749  * This function returns @c EINA_TRUE if @p file can be written, @c EINA_FALSE
750  * otherwise.
751  */
752 EAPI Eina_Bool
753 ecore_file_can_write(const char *file)
754 {
755    if (!file) return EINA_FALSE;
756    if (!access(file, W_OK)) return EINA_TRUE;
757    return EINA_FALSE;
758 }
759
760 /**
761  * @brief Check if the given file can be executed.
762  *
763  * @param  file The name of the file.
764  * @return @c EINA_TRUE if the @p file can be executed, @c EINA_FALSE
765  * otherwise.
766  *
767  * This function returns @c EINA_TRUE if @p file can be executed, @c EINA_FALSE
768  * otherwise.
769  */
770 EAPI Eina_Bool
771 ecore_file_can_exec(const char *file)
772 {
773    if (!file) return EINA_FALSE;
774    if (!access(file, X_OK)) return EINA_TRUE;
775    return EINA_FALSE;
776 }
777
778 /**
779  * @brief Get the path pointed by the given link.
780  *
781  * @param  lnk The name of the link.
782  * @return The path pointed by link or NULL.
783  *
784  * This function returns the path pointed by @p link as a newly
785  * allocated string. This function does not work on Windows. On
786  * failure, the function returns @c NULL. When not needed anymore, the
787  * returned value must be freed.
788  */
789 EAPI char *
790 ecore_file_readlink(const char *lnk)
791 {
792    char buf[PATH_MAX];
793    int count;
794
795    if ((count = readlink(lnk, buf, sizeof(buf) - 1)) < 0) return NULL;
796    buf[count] = 0;
797    return strdup(buf);
798 }
799
800 /**
801  * @brief Get the list of the files and directories in the given
802  * directory.
803  *
804  * @param  dir The name of the directory to list
805  * @return Return an Eina_List containing all the files in the directory;
806  *         on failure it returns NULL.
807  *
808  * This function returns a list of allocated strings of all the files
809  * and directories contained in @p dir. The list will be sorted with
810  * strcoll as compare function. That means that you may want to set
811  * the current locale for the category LC_COLLATE with
812  * setlocale(). For more information see the manual pages of strcoll
813  * and setlocale. The list will not contain the directory entries for
814  * '.' and '..'. On failure, @c NULL is returned. When not needed
815  * anymore, the list elements must be freed.
816  */
817 EAPI Eina_List *
818 ecore_file_ls(const char *dir)
819 {
820    Eina_File_Direct_Info *info;
821    Eina_Iterator *ls;
822    Eina_List *list = NULL;
823
824    ls = eina_file_direct_ls(dir);
825    if (!ls) return NULL;
826
827    EINA_ITERATOR_FOREACH(ls, info)
828      {
829         char *f;
830
831         f = strdup(info->path + info->name_start);
832         list = eina_list_append(list, f);
833      }
834    eina_iterator_free(ls);
835
836    list = eina_list_sort(list, eina_list_count(list), EINA_COMPARE_CB(strcoll));
837
838    return list;
839 }
840
841 /**
842  * @brief Return the executable from the given command.
843  *
844  * @param app The application command, with parameters.
845  * @return The executable from @p app as a newly allocated string. Arguments 
846  * are removed and escape characters are handled. If @p app is @c NULL, or 
847  * on failure, the function returns @c NULL. When not needed anymore, the 
848  * returned value must be freed.
849  */
850 EAPI char *
851 ecore_file_app_exe_get(const char *app)
852 {
853    char *p, *pp, *exe1 = NULL, *exe2 = NULL;
854    char *exe = NULL;
855    int in_quot_dbl = 0, in_quot_sing = 0, restart = 0;
856
857    if (!app) return NULL;
858
859    p = (char *)app;
860 restart:
861    while ((*p) && (isspace((unsigned char)*p))) p++;
862    exe1 = p;
863    while (*p)
864      {
865         if (in_quot_sing)
866           {
867              if (*p == '\'')
868                in_quot_sing = 0;
869           }
870         else if (in_quot_dbl)
871           {
872              if (*p == '\"')
873                in_quot_dbl = 0;
874           }
875         else
876           {
877              if (*p == '\'')
878                in_quot_sing = 1;
879              else if (*p == '\"')
880                in_quot_dbl = 1;
881              if ((isspace((unsigned char)*p)) && ((p <= app) || (p[-1] == '\\')))
882                break;
883           }
884         p++;
885      }
886    exe2 = p;
887    if (exe2 == exe1) return NULL;
888    if (*exe1 == '~')
889      {
890         char *homedir;
891         int len;
892
893         /* Skip ~ */
894         exe1++;
895
896         homedir = getenv("HOME");
897         if (!homedir) return NULL;
898         len = strlen(homedir);
899         if (exe) free(exe);
900         exe = malloc(len + exe2 - exe1 + 2);
901         if (!exe) return NULL;
902         pp = exe;
903         if (len)
904           {
905              strcpy(exe, homedir);
906              pp += len;
907              if (*(pp - 1) != '/')
908                {
909                   *pp = '/';
910                   pp++;
911                }
912           }
913      }
914    else
915      {
916         if (exe) free(exe);
917         exe = malloc(exe2 - exe1 + 1);
918         if (!exe) return NULL;
919         pp = exe;
920      }
921    p = exe1;
922    restart = 0;
923    in_quot_dbl = 0;
924    in_quot_sing = 0;
925    while (*p)
926      {
927         if (in_quot_sing)
928           {
929              if (*p == '\'')
930                in_quot_sing = 0;
931              else
932                {
933                   *pp = *p;
934                   pp++;
935                }
936           }
937         else if (in_quot_dbl)
938           {
939              if (*p == '\"')
940                in_quot_dbl = 0;
941              else
942                {
943                   /* technically this is wrong. double quotes also accept
944                    * special chars:
945                    *
946                    * $, `, \
947                    */
948                   *pp = *p;
949                   pp++;
950                }
951           }
952         else
953           {
954              /* technically we should handle special chars:
955               *
956               * $, `, \, etc.
957               */
958              if ((p > exe1) && (p[-1] == '\\'))
959                {
960                   if (*p != '\n')
961                     {
962                        *pp = *p;
963                        pp++;
964                     }
965                }
966              else if ((p > exe1) && (*p == '='))
967                {
968                   restart = 1;
969                   *pp = *p;
970                   pp++;
971                }
972              else if (*p == '\'')
973                in_quot_sing = 1;
974              else if (*p == '\"')
975                in_quot_dbl = 1;
976              else if (isspace((unsigned char)*p))
977                {
978                   if (restart)
979                     goto restart;
980                   else
981                     break;
982                }
983              else
984                {
985                   *pp = *p;
986                   pp++;
987                }
988           }
989         p++;
990      }
991    *pp = 0;
992    return exe;
993 }
994
995 /**
996  * @brief Add the escape sequence ('\\') to the given file name.
997  *
998  * @param  filename The file name.
999  * @return The file name with special characters escaped.
1000  *
1001  * This function adds the escape sequence ('\\') to the given file
1002  * name and returns the result as a newly allocated string. If the
1003  * length of the returned string is longer than PATH_MAX, or on
1004  * failure, @c NULL is returned. When not needed anymore, the returned
1005  * value must be freed.
1006  */
1007 EAPI char *
1008 ecore_file_escape_name(const char *filename)
1009 {
1010    const char *p;
1011    char *q;
1012    char buf[PATH_MAX];
1013
1014    EINA_SAFETY_ON_NULL_RETURN_VAL(filename, NULL);
1015
1016    p = filename;
1017    q = buf;
1018    while (*p)
1019      {
1020         if ((q - buf) > (PATH_MAX - 6)) return NULL;
1021         if (
1022             (*p == ' ') || (*p == '\\') || (*p == '\'') ||
1023             (*p == '\"') || (*p == ';') || (*p == '!') ||
1024             (*p == '#') || (*p == '$') || (*p == '%') ||
1025             (*p == '&') || (*p == '*') || (*p == '(') ||
1026             (*p == ')') || (*p == '[') || (*p == ']') ||
1027             (*p == '{') || (*p == '}') || (*p == '|') ||
1028             (*p == '<') || (*p == '>') || (*p == '?')
1029             )
1030           {
1031              *q = '\\';
1032              q++;
1033           }
1034         else if (*p == '\t')
1035           {
1036              *q = '\\';
1037              q++;
1038              *q = '\\';
1039              q++;
1040              *q = 't';
1041              q++;
1042              p++;
1043              continue;
1044           }
1045         else if (*p == '\n')
1046           {
1047             *q = '\\';
1048             q++;
1049             *q = '\\';
1050             q++;
1051             *q = 'n';
1052             q++;
1053             p++;
1054             continue;
1055           }
1056
1057         *q = *p;
1058         q++;
1059         p++;
1060      }
1061    *q = 0;
1062    return strdup(buf);
1063 }
1064
1065 /**
1066  * @brief Remove the extension from the given file name.
1067  *
1068  * @param  path The name of the file.
1069  * @return A newly allocated string with the extension stripped out or
1070  * @c NULL on errors.
1071  *
1072  * This function removes the extension from @p path and returns the
1073  * result as a newly allocated string. If @p path is @c NULL, or on
1074  * failure, the function returns @c NULL. When not needed anymore, the
1075  * returned value must be freed.
1076  */
1077 EAPI char *
1078 ecore_file_strip_ext(const char *path)
1079 {
1080    char *p, *file = NULL;
1081
1082    if (!path)
1083      return NULL;
1084
1085    p = strrchr(path, '.');
1086    if (!p)
1087      file = strdup(path);
1088    else if (p != path)
1089      {
1090         file = malloc(((p - path) + 1) * sizeof(char));
1091         if (file)
1092           {
1093              memcpy(file, path, (p - path));
1094              file[p - path] = 0;
1095           }
1096      }
1097
1098    return file;
1099 }
1100
1101 /**
1102  * @brief Check if the given directory is empty.
1103  *
1104  * @param  dir The name of the directory to check.
1105  * @return @c 1 if directory is empty, @c 0 if it has at least one file or
1106  * @c -1 in case of errors.
1107  *
1108  * This functions checks if @p dir is empty. The '.' and '..' files
1109  * will be ignored. If @p dir is empty, 1 is returned, if it contains
1110  * at least one file, @c 0 is returned. On failure, @c -1 is returned.
1111  */
1112 EAPI int
1113 ecore_file_dir_is_empty(const char *dir)
1114 {
1115    Eina_File_Direct_Info *info;
1116    Eina_Iterator *it;
1117
1118    it = eina_file_direct_ls(dir);
1119    if (!it) return -1;
1120
1121    EINA_ITERATOR_FOREACH(it, info)
1122      {
1123         eina_iterator_free(it);
1124         return 0;
1125      }
1126
1127    eina_iterator_free(it);
1128    return 1;
1129 }
1130
1131 /**
1132  * @}
1133  */