Avoid memory leaks in borderline cases. (#172612, Morten Welinder)
[platform/upstream/glib.git] / glib / gfileutils.c
1 /* gfileutils.c - File utility functions
2  *
3  *  Copyright 2000 Red Hat, Inc.
4  *
5  * GLib is free software; you can redistribute it and/or modify it
6  * under the terms of the GNU Lesser General Public License as
7  * published by the Free Software Foundation; either version 2 of the
8  * License, or (at your option) any later version.
9  *
10  * GLib is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13  * Lesser General Public License for more details.
14  *
15  * You should have received a copy of the GNU Lesser General Public
16  * License along with GLib; see the file COPYING.LIB.  If not,
17  * write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18  *   Boston, MA 02111-1307, USA.
19  */
20
21 #include "config.h"
22
23 #include "glib.h"
24
25 #include <sys/stat.h>
26 #ifdef HAVE_UNISTD_H
27 #include <unistd.h>
28 #endif
29 #include <stdio.h>
30 #include <stdlib.h>
31 #include <stdarg.h>
32 #include <string.h>
33 #include <errno.h>
34 #include <sys/types.h>
35 #include <sys/stat.h>
36 #include <fcntl.h>
37 #include <stdlib.h>
38
39 #ifdef G_OS_WIN32
40 #include <windows.h>
41 #include <io.h>
42 #endif /* G_OS_WIN32 */
43
44 #ifndef S_ISLNK
45 #define S_ISLNK(x) 0
46 #endif
47
48 #ifndef O_BINARY
49 #define O_BINARY 0
50 #endif
51
52 #include "gstdio.h"
53 #include "glibintl.h"
54
55 #include "galias.h"
56
57 /**
58  * g_file_test:
59  * @filename: a filename to test in the GLib file name encoding
60  * @test: bitfield of #GFileTest flags
61  * 
62  * Returns %TRUE if any of the tests in the bitfield @test are
63  * %TRUE. For example, <literal>(G_FILE_TEST_EXISTS | 
64  * G_FILE_TEST_IS_DIR)</literal> will return %TRUE if the file exists; 
65  * the check whether it's a directory doesn't matter since the existence 
66  * test is %TRUE. With the current set of available tests, there's no point
67  * passing in more than one test at a time.
68  * 
69  * Apart from %G_FILE_TEST_IS_SYMLINK all tests follow symbolic links,
70  * so for a symbolic link to a regular file g_file_test() will return
71  * %TRUE for both %G_FILE_TEST_IS_SYMLINK and %G_FILE_TEST_IS_REGULAR.
72  *
73  * Note, that for a dangling symbolic link g_file_test() will return
74  * %TRUE for %G_FILE_TEST_IS_SYMLINK and %FALSE for all other flags.
75  *
76  * You should never use g_file_test() to test whether it is safe
77  * to perform an operation, because there is always the possibility
78  * of the condition changing before you actually perform the operation.
79  * For example, you might think you could use %G_FILE_TEST_IS_SYMLINK
80  * to know whether it is is safe to write to a file without being
81  * tricked into writing into a different location. It doesn't work!
82  *
83  * <informalexample><programlisting>
84  * /&ast; DON'T DO THIS &ast;/
85  *  if (!g_file_test (filename, G_FILE_TEST_IS_SYMLINK)) {
86  *    fd = g_open (filename, O_WRONLY);
87  *    /&ast; write to fd &ast;/
88  *  }
89  * </programlisting></informalexample>
90  *
91  * Another thing to note is that %G_FILE_TEST_EXISTS and
92  * %G_FILE_TEST_IS_EXECUTABLE are implemented using the access()
93  * system call. This usually doesn't matter, but if your program
94  * is setuid or setgid it means that these tests will give you
95  * the answer for the real user ID and group ID, rather than the
96  * effective user ID and group ID.
97  *
98  * On Windows, there are no symlinks, so testing for
99  * %G_FILE_TEST_IS_SYMLINK will always return %FALSE. Testing for
100  * %G_FILE_TEST_IS_EXECUTABLE will just check that the file exists and
101  * its name indicates that it is executable, checking for well-known
102  * extensions and those listed in the %PATHEXT environment variable.
103  *
104  * Return value: whether a test was %TRUE
105  **/
106 gboolean
107 g_file_test (const gchar *filename,
108              GFileTest    test)
109 {
110 #ifdef G_OS_WIN32
111 /* stuff missing in std vc6 api */
112 #  ifndef INVALID_FILE_ATTRIBUTES
113 #    define INVALID_FILE_ATTRIBUTES -1
114 #  endif
115 #  ifndef FILE_ATTRIBUTE_DEVICE
116 #    define FILE_ATTRIBUTE_DEVICE 64
117 #  endif
118   int attributes;
119
120   if (G_WIN32_HAVE_WIDECHAR_API ())
121     {
122       wchar_t *wfilename = g_utf8_to_utf16 (filename, -1, NULL, NULL, NULL);
123
124       if (wfilename == NULL)
125         return FALSE;
126
127       attributes = GetFileAttributesW (wfilename);
128
129       g_free (wfilename);
130     }
131   else
132     {
133       gchar *cpfilename = g_locale_from_utf8 (filename, -1, NULL, NULL, NULL);
134
135       if (cpfilename == NULL)
136         return FALSE;
137       
138       attributes = GetFileAttributesA (cpfilename);
139       
140       g_free (cpfilename);
141     }
142
143   if (attributes == INVALID_FILE_ATTRIBUTES)
144     return FALSE;
145
146   if (test & G_FILE_TEST_EXISTS)
147     return TRUE;
148       
149   if (test & G_FILE_TEST_IS_REGULAR)
150     return (attributes & (FILE_ATTRIBUTE_DIRECTORY | FILE_ATTRIBUTE_DEVICE)) == 0;
151
152   if (test & G_FILE_TEST_IS_DIR)
153     return (attributes & FILE_ATTRIBUTE_DIRECTORY) != 0;
154
155   if (test & G_FILE_TEST_IS_EXECUTABLE)
156     {
157       const gchar *lastdot = strrchr (filename, '.');
158       const gchar *pathext = NULL, *p;
159       int extlen;
160
161       if (lastdot == NULL)
162         return FALSE;
163
164       if (stricmp (lastdot, ".exe") == 0 ||
165           stricmp (lastdot, ".cmd") == 0 ||
166           stricmp (lastdot, ".bat") == 0 ||
167           stricmp (lastdot, ".com") == 0)
168         return TRUE;
169
170       /* Check if it is one of the types listed in %PATHEXT% */
171
172       pathext = g_getenv ("PATHEXT");
173       if (pathext == NULL)
174         return FALSE;
175
176       pathext = g_utf8_casefold (pathext, -1);
177
178       lastdot = g_utf8_casefold (lastdot, -1);
179       extlen = strlen (lastdot);
180
181       p = pathext;
182       while (TRUE)
183         {
184           const gchar *q = strchr (p, ';');
185           if (q == NULL)
186             q = p + strlen (p);
187           if (extlen == q - p &&
188               memcmp (lastdot, p, extlen) == 0)
189             {
190               g_free ((gchar *) pathext);
191               g_free ((gchar *) lastdot);
192               return TRUE;
193             }
194           if (*q)
195             p = q + 1;
196           else
197             break;
198         }
199
200       g_free ((gchar *) pathext);
201       g_free ((gchar *) lastdot);
202       return FALSE;
203     }
204
205   return FALSE;
206 #else
207   if ((test & G_FILE_TEST_EXISTS) && (access (filename, F_OK) == 0))
208     return TRUE;
209   
210   if ((test & G_FILE_TEST_IS_EXECUTABLE) && (access (filename, X_OK) == 0))
211     {
212       if (getuid () != 0)
213         return TRUE;
214
215       /* For root, on some POSIX systems, access (filename, X_OK)
216        * will succeed even if no executable bits are set on the
217        * file. We fall through to a stat test to avoid that.
218        */
219     }
220   else
221     test &= ~G_FILE_TEST_IS_EXECUTABLE;
222
223   if (test & G_FILE_TEST_IS_SYMLINK)
224     {
225       struct stat s;
226
227       if ((lstat (filename, &s) == 0) && S_ISLNK (s.st_mode))
228         return TRUE;
229     }
230   
231   if (test & (G_FILE_TEST_IS_REGULAR |
232               G_FILE_TEST_IS_DIR |
233               G_FILE_TEST_IS_EXECUTABLE))
234     {
235       struct stat s;
236       
237       if (stat (filename, &s) == 0)
238         {
239           if ((test & G_FILE_TEST_IS_REGULAR) && S_ISREG (s.st_mode))
240             return TRUE;
241           
242           if ((test & G_FILE_TEST_IS_DIR) && S_ISDIR (s.st_mode))
243             return TRUE;
244
245           /* The extra test for root when access (file, X_OK) succeeds.
246            */
247           if ((test & G_FILE_TEST_IS_EXECUTABLE) &&
248               ((s.st_mode & S_IXOTH) ||
249                (s.st_mode & S_IXUSR) ||
250                (s.st_mode & S_IXGRP)))
251             return TRUE;
252         }
253     }
254
255   return FALSE;
256 #endif
257 }
258
259 #ifdef G_OS_WIN32
260
261 #undef g_file_test
262
263 /* Binary compatibility version. Not for newly compiled code. */
264
265 gboolean
266 g_file_test (const gchar *filename,
267              GFileTest    test)
268 {
269   gchar *utf8_filename = g_locale_to_utf8 (filename, -1, NULL, NULL, NULL);
270   gboolean retval;
271
272   if (utf8_filename == NULL)
273     return FALSE;
274
275   retval = g_file_test_utf8 (utf8_filename, test);
276
277   g_free (utf8_filename);
278
279   return retval;
280 }
281
282 #endif
283
284 GQuark
285 g_file_error_quark (void)
286 {
287   static GQuark q = 0;
288   if (q == 0)
289     q = g_quark_from_static_string ("g-file-error-quark");
290
291   return q;
292 }
293
294 /**
295  * g_file_error_from_errno:
296  * @err_no: an "errno" value
297  * 
298  * Gets a #GFileError constant based on the passed-in @errno.
299  * For example, if you pass in %EEXIST this function returns
300  * #G_FILE_ERROR_EXIST. Unlike @errno values, you can portably
301  * assume that all #GFileError values will exist.
302  *
303  * Normally a #GFileError value goes into a #GError returned
304  * from a function that manipulates files. So you would use
305  * g_file_error_from_errno() when constructing a #GError.
306  * 
307  * Return value: #GFileError corresponding to the given @errno
308  **/
309 GFileError
310 g_file_error_from_errno (gint err_no)
311 {
312   switch (err_no)
313     {
314 #ifdef EEXIST
315     case EEXIST:
316       return G_FILE_ERROR_EXIST;
317       break;
318 #endif
319
320 #ifdef EISDIR
321     case EISDIR:
322       return G_FILE_ERROR_ISDIR;
323       break;
324 #endif
325
326 #ifdef EACCES
327     case EACCES:
328       return G_FILE_ERROR_ACCES;
329       break;
330 #endif
331
332 #ifdef ENAMETOOLONG
333     case ENAMETOOLONG:
334       return G_FILE_ERROR_NAMETOOLONG;
335       break;
336 #endif
337
338 #ifdef ENOENT
339     case ENOENT:
340       return G_FILE_ERROR_NOENT;
341       break;
342 #endif
343
344 #ifdef ENOTDIR
345     case ENOTDIR:
346       return G_FILE_ERROR_NOTDIR;
347       break;
348 #endif
349
350 #ifdef ENXIO
351     case ENXIO:
352       return G_FILE_ERROR_NXIO;
353       break;
354 #endif
355
356 #ifdef ENODEV
357     case ENODEV:
358       return G_FILE_ERROR_NODEV;
359       break;
360 #endif
361
362 #ifdef EROFS
363     case EROFS:
364       return G_FILE_ERROR_ROFS;
365       break;
366 #endif
367
368 #ifdef ETXTBSY
369     case ETXTBSY:
370       return G_FILE_ERROR_TXTBSY;
371       break;
372 #endif
373
374 #ifdef EFAULT
375     case EFAULT:
376       return G_FILE_ERROR_FAULT;
377       break;
378 #endif
379
380 #ifdef ELOOP
381     case ELOOP:
382       return G_FILE_ERROR_LOOP;
383       break;
384 #endif
385
386 #ifdef ENOSPC
387     case ENOSPC:
388       return G_FILE_ERROR_NOSPC;
389       break;
390 #endif
391
392 #ifdef ENOMEM
393     case ENOMEM:
394       return G_FILE_ERROR_NOMEM;
395       break;
396 #endif
397
398 #ifdef EMFILE
399     case EMFILE:
400       return G_FILE_ERROR_MFILE;
401       break;
402 #endif
403
404 #ifdef ENFILE
405     case ENFILE:
406       return G_FILE_ERROR_NFILE;
407       break;
408 #endif
409
410 #ifdef EBADF
411     case EBADF:
412       return G_FILE_ERROR_BADF;
413       break;
414 #endif
415
416 #ifdef EINVAL
417     case EINVAL:
418       return G_FILE_ERROR_INVAL;
419       break;
420 #endif
421
422 #ifdef EPIPE
423     case EPIPE:
424       return G_FILE_ERROR_PIPE;
425       break;
426 #endif
427
428 #ifdef EAGAIN
429     case EAGAIN:
430       return G_FILE_ERROR_AGAIN;
431       break;
432 #endif
433
434 #ifdef EINTR
435     case EINTR:
436       return G_FILE_ERROR_INTR;
437       break;
438 #endif
439
440 #ifdef EIO
441     case EIO:
442       return G_FILE_ERROR_IO;
443       break;
444 #endif
445
446 #ifdef EPERM
447     case EPERM:
448       return G_FILE_ERROR_PERM;
449       break;
450 #endif
451
452 #ifdef ENOSYS
453     case ENOSYS:
454       return G_FILE_ERROR_NOSYS;
455       break;
456 #endif
457
458     default:
459       return G_FILE_ERROR_FAILED;
460       break;
461     }
462 }
463
464 static gboolean
465 get_contents_stdio (const gchar *display_filename,
466                     FILE        *f,
467                     gchar      **contents,
468                     gsize       *length,
469                     GError     **error)
470 {
471   gchar buf[4096];
472   size_t bytes;
473   gchar *str = NULL;
474   size_t total_bytes = 0;
475   size_t total_allocated = 0;
476   gchar *tmp;
477
478   g_assert (f != NULL);
479
480   while (!feof (f))
481     {
482       gint save_errno;
483
484       bytes = fread (buf, 1, sizeof (buf), f);
485       save_errno = errno;
486
487       while ((total_bytes + bytes + 1) > total_allocated)
488         {
489           if (str)
490             total_allocated *= 2;
491           else
492             total_allocated = MIN (bytes + 1, sizeof (buf));
493
494           tmp = g_try_realloc (str, total_allocated);
495
496           if (tmp == NULL)
497             {
498               g_set_error (error,
499                            G_FILE_ERROR,
500                            G_FILE_ERROR_NOMEM,
501                            _("Could not allocate %lu bytes to read file \"%s\""),
502                            (gulong) total_allocated,
503                            display_filename);
504
505               goto error;
506             }
507
508           str = tmp;
509         }
510
511       if (ferror (f))
512         {
513           g_set_error (error,
514                        G_FILE_ERROR,
515                        g_file_error_from_errno (save_errno),
516                        _("Error reading file '%s': %s"),
517                        display_filename,
518                        g_strerror (save_errno));
519
520           goto error;
521         }
522
523       memcpy (str + total_bytes, buf, bytes);
524       total_bytes += bytes;
525     }
526
527   fclose (f);
528
529   if (total_allocated == 0)
530     str = g_new (gchar, 1);
531
532   str[total_bytes] = '\0';
533
534   if (length)
535     *length = total_bytes;
536
537   *contents = str;
538
539   return TRUE;
540
541  error:
542
543   g_free (str);
544   fclose (f);
545
546   return FALSE;
547 }
548
549 #ifndef G_OS_WIN32
550
551 static gboolean
552 get_contents_regfile (const gchar *display_filename,
553                       struct stat *stat_buf,
554                       gint         fd,
555                       gchar      **contents,
556                       gsize       *length,
557                       GError     **error)
558 {
559   gchar *buf;
560   size_t bytes_read;
561   size_t size;
562   size_t alloc_size;
563   
564   size = stat_buf->st_size;
565
566   alloc_size = size + 1;
567   buf = g_try_malloc (alloc_size);
568
569   if (buf == NULL)
570     {
571       g_set_error (error,
572                    G_FILE_ERROR,
573                    G_FILE_ERROR_NOMEM,
574                    _("Could not allocate %lu bytes to read file \"%s\""),
575                    (gulong) alloc_size, 
576                    display_filename);
577
578       goto error;
579     }
580   
581   bytes_read = 0;
582   while (bytes_read < size)
583     {
584       gssize rc;
585           
586       rc = read (fd, buf + bytes_read, size - bytes_read);
587
588       if (rc < 0)
589         {
590           if (errno != EINTR) 
591             {
592               int save_errno = errno;
593
594               g_free (buf);
595               g_set_error (error,
596                            G_FILE_ERROR,
597                            g_file_error_from_errno (save_errno),
598                            _("Failed to read from file '%s': %s"),
599                            display_filename, 
600                            g_strerror (save_errno));
601
602               goto error;
603             }
604         }
605       else if (rc == 0)
606         break;
607       else
608         bytes_read += rc;
609     }
610       
611   buf[bytes_read] = '\0';
612
613   if (length)
614     *length = bytes_read;
615   
616   *contents = buf;
617
618   close (fd);
619
620   return TRUE;
621
622  error:
623
624   close (fd);
625   
626   return FALSE;
627 }
628
629 static gboolean
630 get_contents_posix (const gchar *filename,
631                     gchar      **contents,
632                     gsize       *length,
633                     GError     **error)
634 {
635   struct stat stat_buf;
636   gint fd;
637   gchar *display_filename = g_filename_display_name (filename);
638
639   /* O_BINARY useful on Cygwin */
640   fd = open (filename, O_RDONLY|O_BINARY);
641
642   if (fd < 0)
643     {
644       int save_errno = errno;
645
646       g_set_error (error,
647                    G_FILE_ERROR,
648                    g_file_error_from_errno (save_errno),
649                    _("Failed to open file '%s': %s"),
650                    display_filename, 
651                    g_strerror (save_errno));
652       g_free (display_filename);
653
654       return FALSE;
655     }
656
657   /* I don't think this will ever fail, aside from ENOMEM, but. */
658   if (fstat (fd, &stat_buf) < 0)
659     {
660       int save_errno = errno;
661
662       close (fd);
663       g_set_error (error,
664                    G_FILE_ERROR,
665                    g_file_error_from_errno (save_errno),
666                    _("Failed to get attributes of file '%s': fstat() failed: %s"),
667                    display_filename, 
668                    g_strerror (save_errno));
669       g_free (display_filename);
670
671       return FALSE;
672     }
673
674   if (stat_buf.st_size > 0 && S_ISREG (stat_buf.st_mode))
675     {
676       gboolean retval = get_contents_regfile (display_filename,
677                                               &stat_buf,
678                                               fd,
679                                               contents,
680                                               length,
681                                               error);
682       g_free (display_filename);
683
684       return retval;
685     }
686   else
687     {
688       FILE *f;
689       gboolean retval;
690
691       f = fdopen (fd, "r");
692       
693       if (f == NULL)
694         {
695           int save_errno = errno;
696
697           g_set_error (error,
698                        G_FILE_ERROR,
699                        g_file_error_from_errno (save_errno),
700                        _("Failed to open file '%s': fdopen() failed: %s"),
701                        display_filename, 
702                        g_strerror (save_errno));
703           g_free (display_filename);
704
705           return FALSE;
706         }
707   
708       retval = get_contents_stdio (display_filename, f, contents, length, error);
709       g_free (display_filename);
710
711       return retval;
712     }
713 }
714
715 #else  /* G_OS_WIN32 */
716
717 static gboolean
718 get_contents_win32 (const gchar *filename,
719                     gchar      **contents,
720                     gsize       *length,
721                     GError     **error)
722 {
723   FILE *f;
724   gboolean retval;
725   gchar *display_filename = g_filename_display_name (filename);
726   int save_errno;
727   
728   f = g_fopen (filename, "rb");
729   save_errno = errno;
730
731   if (f == NULL)
732     {
733       g_set_error (error,
734                    G_FILE_ERROR,
735                    g_file_error_from_errno (save_errno),
736                    _("Failed to open file '%s': %s"),
737                    display_filename,
738                    g_strerror (save_errno));
739       g_free (display_filename);
740
741       return FALSE;
742     }
743   
744   retval = get_contents_stdio (display_filename, f, contents, length, error);
745   g_free (display_filename);
746
747   return retval;
748 }
749
750 #endif
751
752 /**
753  * g_file_get_contents:
754  * @filename: name of a file to read contents from, in the GLib file name encoding
755  * @contents: location to store an allocated string
756  * @length: location to store length in bytes of the contents, or %NULL
757  * @error: return location for a #GError, or %NULL
758  * 
759  * Reads an entire file into allocated memory, with good error
760  * checking. 
761  *
762  * If the call was successful, it returns %TRUE and sets @contents to the file 
763  * contents and @length to the length of the file contents in bytes. The string 
764  * stored in @contents will be nul-terminated, so for text files you can pass 
765  * %NULL for the @length argument. If the call was not successful, it returns 
766  * %FALSE and sets @error. The error domain is #G_FILE_ERROR. Possible error  
767  * codes are those in the #GFileError enumeration. In the error case, 
768  * @contents is set to %NULL and @length is set to zero.
769  *
770  * Return value: %TRUE on success, %FALSE if an error occurred
771  **/
772 gboolean
773 g_file_get_contents (const gchar *filename,
774                      gchar      **contents,
775                      gsize       *length,
776                      GError     **error)
777 {  
778   g_return_val_if_fail (filename != NULL, FALSE);
779   g_return_val_if_fail (contents != NULL, FALSE);
780
781   *contents = NULL;
782   if (length)
783     *length = 0;
784
785 #ifdef G_OS_WIN32
786   return get_contents_win32 (filename, contents, length, error);
787 #else
788   return get_contents_posix (filename, contents, length, error);
789 #endif
790 }
791
792 #ifdef G_OS_WIN32
793
794 #undef g_file_get_contents
795
796 /* Binary compatibility version. Not for newly compiled code. */
797
798 gboolean
799 g_file_get_contents (const gchar *filename,
800                      gchar      **contents,
801                      gsize       *length,
802                      GError     **error)
803 {
804   gchar *utf8_filename = g_locale_to_utf8 (filename, -1, NULL, NULL, error);
805   gboolean retval;
806
807   if (utf8_filename == NULL)
808     return FALSE;
809
810   retval = g_file_get_contents_utf8 (utf8_filename, contents, length, error);
811
812   g_free (utf8_filename);
813
814   return retval;
815 }
816
817 #endif
818
819
820 static gboolean
821 rename_file (const char *old_name,
822              const char *new_name,
823              GError **err)
824 {
825   errno = 0;
826   if (g_rename (old_name, new_name) == -1)
827     {
828       int save_errno = errno;
829       gchar *display_old_name = g_filename_display_name (old_name);
830       gchar *display_new_name = g_filename_display_name (new_name);
831       
832       g_set_error (err,
833                    G_FILE_ERROR,
834                    g_file_error_from_errno (save_errno),
835                    _("Failed to rename file '%s' to '%s': g_rename() failed: %s"),
836                    display_old_name,
837                    display_new_name,
838                    g_strerror (save_errno));
839
840       g_free (display_old_name);
841       g_free (display_new_name);
842       
843       return FALSE;
844     }
845   
846   return TRUE;
847 }
848
849 static gchar *
850 write_to_temp_file (const gchar *contents,
851                     gssize length,
852                     const gchar *template,
853                     GError **err)
854 {
855   gchar *tmp_name;
856   gchar *display_name;
857   gchar *retval;
858   FILE *file;
859   gint fd;
860   int save_errno;
861
862   retval = NULL;
863   
864   tmp_name = g_strdup_printf ("%s.XXXXXX", template);
865
866   errno = 0;
867   fd = g_mkstemp (tmp_name);
868   save_errno = errno;
869   display_name = g_filename_display_name (tmp_name);
870       
871   if (fd == -1)
872     {
873       g_set_error (err,
874                    G_FILE_ERROR,
875                    g_file_error_from_errno (save_errno),
876                    _("Failed to create file '%s': %s"),
877                    display_name, g_strerror (save_errno));
878       
879       goto out;
880     }
881
882   errno = 0;
883   file = fdopen (fd, "wb");
884   if (!file)
885     {
886       g_set_error (err,
887                    G_FILE_ERROR,
888                    g_file_error_from_errno (errno),
889                    _("Failed to open file '%s' for writing: fdopen() failed: %s"),
890                    display_name,
891                    g_strerror (errno));
892
893       close (fd);
894       g_unlink (tmp_name);
895       
896       goto out;
897     }
898
899   if (length > 0)
900     {
901       size_t n_written;
902       
903       errno = 0;
904
905       n_written = fwrite (contents, 1, length, file);
906       
907       if (n_written < length)
908         {
909           g_set_error (err,
910                        G_FILE_ERROR,
911                        g_file_error_from_errno (errno),
912                        _("Failed to write file '%s': fwrite() failed: %s"),
913                        display_name,
914                        g_strerror (errno));
915
916           fclose (file);
917           g_unlink (tmp_name);
918           
919           goto out;
920         }
921     }
922    
923   errno = 0;
924   if (fclose (file) == EOF)
925     {
926       g_set_error (err,
927                    G_FILE_ERROR,
928                    g_file_error_from_errno (errno),
929                    _("Failed to close file '%s': fclose() failed: %s"),
930                    display_name, 
931                    g_strerror (errno));
932
933       g_unlink (tmp_name);
934       
935       goto out;
936     }
937   
938   retval = g_strdup (tmp_name);
939
940  out:
941   g_free (tmp_name);
942   g_free (display_name);
943   
944   return retval;
945 }
946
947 /**
948  * g_file_replace:
949  * @filename: name of a file to write @contents to, in the GLib file name
950  *   encoding
951  * @contents: string to write to the file
952  * @length: length of @contents, or -1 if @contents is a nul-terminated string
953  * @error: return location for a #GError, or %NULL
954  *
955  * Writes all of @contents to a file named @filename, with good error checking.
956  * If a file called @filename already exists it will be overwritten.
957  *
958  * This write is atomic in the sense that it is first written to a temporary
959  * file which is then renamed to the final name. Notes:
960  * <itemizedlist>
961  * <listitem>
962  *    On Unix, if @filename already exists hard links to @filename will break.
963  *    Also since the file is recreated, existing permissions, access control
964  *    lists, metadata etc. may be lost. If @filename is a symbolic link,
965  *    the link itself will be replaced, not the linked file.
966  * </listitem>
967  * <listitem>
968  *   On Windows renaming a file will not remove an existing file with the
969  *   new name, so on Windows there is a race condition between the existing
970  *   file being removed and the temporary file being renamed.
971  * </listitem>
972  * <listitem>
973  *   On Windows there is no way to remove a file that is open to some
974  *   process, or mapped into memory. Thus, this function will fail if
975  *   @filename already exists and is open.
976  * </listitem>
977  * </itemizedlist>
978  *
979  * If the call was sucessful, it returns %TRUE. If the call was not successful,
980  * it returns %FALSE and sets @error. The error domain is #G_FILE_ERROR.
981  * Possible error codes are those in the #GFileError enumeration.
982  *
983  * Return value: %TRUE on success, %FALSE if an error occurred
984  *
985  * Since: 2.8
986  **/
987 gboolean
988 g_file_replace (const gchar *filename,
989                 const gchar *contents,
990                 gssize       length,
991                 GError     **error)
992 {
993   gchar *tmp_filename;
994   gboolean retval;
995   GError *rename_error = NULL;
996   
997   g_return_val_if_fail (filename != NULL, FALSE);
998   g_return_val_if_fail (error == NULL || *error == NULL, FALSE);
999   g_return_val_if_fail (contents != NULL || length == 0, FALSE);
1000   g_return_val_if_fail (length >= -1, FALSE);
1001   
1002   if (length == -1)
1003     length = strlen (contents);
1004
1005   tmp_filename = write_to_temp_file (contents, length, filename, error);
1006   
1007   if (!tmp_filename)
1008     {
1009       retval = FALSE;
1010       goto out;
1011     }
1012
1013   if (!rename_file (tmp_filename, filename, &rename_error))
1014     {
1015 #ifndef G_OS_WIN32
1016
1017       g_unlink (tmp_filename);
1018       g_propagate_error (error, rename_error);
1019       retval = FALSE;
1020       goto out;
1021
1022 #else /* G_OS_WIN32 */
1023       
1024       /* Renaming failed, but on Windows this may just mean
1025        * the file already exists. So if the target file
1026        * exists, try deleting it and do the rename again.
1027        */
1028       if (!g_file_test (filename, G_FILE_TEST_EXISTS))
1029         {
1030           g_unlink (tmp_filename);
1031           g_propagate_error (error, rename_error);
1032           retval = FALSE;
1033           goto out;
1034         }
1035
1036       g_error_free (rename_error);
1037       
1038       if (g_unlink (filename) == -1)
1039         {
1040           gchar *display_filename = g_filename_display_name (filename);
1041
1042           g_set_error (error,
1043                        G_FILE_ERROR,
1044                        g_file_error_from_errno (errno),
1045                        _("Existing file '%s' could not be removed: g_unlink() failed: %s"),
1046                        display_filename,
1047                        g_strerror (errno));
1048
1049           g_free (display_filename);
1050           g_unlink (tmp_filename);
1051           retval = FALSE;
1052           goto out;
1053         }
1054       
1055       if (!rename_file (tmp_filename, filename, error))
1056         {
1057           g_unlink (tmp_filename);
1058           retval = FALSE;
1059           goto out;
1060         }
1061
1062 #endif
1063     }
1064
1065   retval = TRUE;
1066   
1067  out:
1068   g_free (tmp_filename);
1069   return retval;
1070 }
1071
1072 /*
1073  * mkstemp() implementation is from the GNU C library.
1074  * Copyright (C) 1991,92,93,94,95,96,97,98,99 Free Software Foundation, Inc.
1075  */
1076 /**
1077  * g_mkstemp:
1078  * @tmpl: template filename
1079  *
1080  * Opens a temporary file. See the mkstemp() documentation
1081  * on most UNIX-like systems. This is a portability wrapper, which simply calls 
1082  * mkstemp() on systems that have it, and implements 
1083  * it in GLib otherwise.
1084  *
1085  * The parameter is a string that should match the rules for
1086  * mkstemp(), i.e. end in "XXXXXX". The X string will 
1087  * be modified to form the name of a file that didn't exist.
1088  * The string should be in the GLib file name encoding. Most importantly, 
1089  * on Windows it should be in UTF-8.
1090  *
1091  * Return value: A file handle (as from open()) to the file
1092  * opened for reading and writing. The file is opened in binary mode
1093  * on platforms where there is a difference. The file handle should be
1094  * closed with close(). In case of errors, -1 is returned.
1095  */
1096 gint
1097 g_mkstemp (gchar *tmpl)
1098 {
1099 #ifdef HAVE_MKSTEMP
1100   return mkstemp (tmpl);
1101 #else
1102   int len;
1103   char *XXXXXX;
1104   int count, fd;
1105   static const char letters[] =
1106     "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";
1107   static const int NLETTERS = sizeof (letters) - 1;
1108   glong value;
1109   GTimeVal tv;
1110   static int counter = 0;
1111
1112   len = strlen (tmpl);
1113   if (len < 6 || strcmp (&tmpl[len - 6], "XXXXXX"))
1114     {
1115       errno = EINVAL;
1116       return -1;
1117     }
1118
1119   /* This is where the Xs start.  */
1120   XXXXXX = &tmpl[len - 6];
1121
1122   /* Get some more or less random data.  */
1123   g_get_current_time (&tv);
1124   value = (tv.tv_usec ^ tv.tv_sec) + counter++;
1125
1126   for (count = 0; count < 100; value += 7777, ++count)
1127     {
1128       glong v = value;
1129
1130       /* Fill in the random bits.  */
1131       XXXXXX[0] = letters[v % NLETTERS];
1132       v /= NLETTERS;
1133       XXXXXX[1] = letters[v % NLETTERS];
1134       v /= NLETTERS;
1135       XXXXXX[2] = letters[v % NLETTERS];
1136       v /= NLETTERS;
1137       XXXXXX[3] = letters[v % NLETTERS];
1138       v /= NLETTERS;
1139       XXXXXX[4] = letters[v % NLETTERS];
1140       v /= NLETTERS;
1141       XXXXXX[5] = letters[v % NLETTERS];
1142
1143       /* tmpl is in UTF-8 on Windows, thus use g_open() */
1144       fd = g_open (tmpl, O_RDWR | O_CREAT | O_EXCL | O_BINARY, 0600);
1145
1146       if (fd >= 0)
1147         return fd;
1148       else if (errno != EEXIST)
1149         /* Any other error will apply also to other names we might
1150          *  try, and there are 2^32 or so of them, so give up now.
1151          */
1152         return -1;
1153     }
1154
1155   /* We got out of the loop because we ran out of combinations to try.  */
1156   errno = EEXIST;
1157   return -1;
1158 #endif
1159 }
1160
1161 #ifdef G_OS_WIN32
1162
1163 #undef g_mkstemp
1164
1165 /* Binary compatibility version. Not for newly compiled code. */
1166
1167 gint
1168 g_mkstemp (gchar *tmpl)
1169 {
1170   int len;
1171   char *XXXXXX;
1172   int count, fd;
1173   static const char letters[] =
1174     "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";
1175   static const int NLETTERS = sizeof (letters) - 1;
1176   glong value;
1177   GTimeVal tv;
1178   static int counter = 0;
1179
1180   len = strlen (tmpl);
1181   if (len < 6 || strcmp (&tmpl[len - 6], "XXXXXX"))
1182     {
1183       errno = EINVAL;
1184       return -1;
1185     }
1186
1187   /* This is where the Xs start.  */
1188   XXXXXX = &tmpl[len - 6];
1189
1190   /* Get some more or less random data.  */
1191   g_get_current_time (&tv);
1192   value = (tv.tv_usec ^ tv.tv_sec) + counter++;
1193
1194   for (count = 0; count < 100; value += 7777, ++count)
1195     {
1196       glong v = value;
1197
1198       /* Fill in the random bits.  */
1199       XXXXXX[0] = letters[v % NLETTERS];
1200       v /= NLETTERS;
1201       XXXXXX[1] = letters[v % NLETTERS];
1202       v /= NLETTERS;
1203       XXXXXX[2] = letters[v % NLETTERS];
1204       v /= NLETTERS;
1205       XXXXXX[3] = letters[v % NLETTERS];
1206       v /= NLETTERS;
1207       XXXXXX[4] = letters[v % NLETTERS];
1208       v /= NLETTERS;
1209       XXXXXX[5] = letters[v % NLETTERS];
1210
1211       /* This is the backward compatibility system codepage version,
1212        * thus use normal open().
1213        */
1214       fd = open (tmpl, O_RDWR | O_CREAT | O_EXCL | O_BINARY, 0600);
1215
1216       if (fd >= 0)
1217         return fd;
1218       else if (errno != EEXIST)
1219         /* Any other error will apply also to other names we might
1220          *  try, and there are 2^32 or so of them, so give up now.
1221          */
1222         return -1;
1223     }
1224
1225   /* We got out of the loop because we ran out of combinations to try.  */
1226   errno = EEXIST;
1227   return -1;
1228 }
1229
1230 #endif
1231
1232 /**
1233  * g_file_open_tmp:
1234  * @tmpl: Template for file name, as in g_mkstemp(), basename only
1235  * @name_used: location to store actual name used
1236  * @error: return location for a #GError
1237  *
1238  * Opens a file for writing in the preferred directory for temporary
1239  * files (as returned by g_get_tmp_dir()). 
1240  *
1241  * @tmpl should be a string in the GLib file name encoding ending with
1242  * six 'X' characters, as the parameter to g_mkstemp() (or mkstemp()).
1243  * However, unlike these functions, the template should only be a
1244  * basename, no directory components are allowed. If template is
1245  * %NULL, a default template is used.
1246  *
1247  * Note that in contrast to g_mkstemp() (and mkstemp()) 
1248  * @tmpl is not modified, and might thus be a read-only literal string.
1249  *
1250  * The actual name used is returned in @name_used if non-%NULL. This
1251  * string should be freed with g_free() when not needed any longer.
1252  * The returned name is in the GLib file name encoding.
1253  *
1254  * Return value: A file handle (as from open()) to 
1255  * the file opened for reading and writing. The file is opened in binary 
1256  * mode on platforms where there is a difference. The file handle should be
1257  * closed with close(). In case of errors, -1 is returned 
1258  * and @error will be set.
1259  **/
1260 gint
1261 g_file_open_tmp (const gchar *tmpl,
1262                  gchar      **name_used,
1263                  GError     **error)
1264 {
1265   int retval;
1266   const char *tmpdir;
1267   char *sep;
1268   char *fulltemplate;
1269   const char *slash;
1270
1271   if (tmpl == NULL)
1272     tmpl = ".XXXXXX";
1273
1274   if ((slash = strchr (tmpl, G_DIR_SEPARATOR)) != NULL
1275 #ifdef G_OS_WIN32
1276       || (strchr (tmpl, '/') != NULL && (slash = "/"))
1277 #endif
1278       )
1279     {
1280       gchar *display_tmpl = g_filename_display_name (tmpl);
1281       char c[2];
1282       c[0] = *slash;
1283       c[1] = '\0';
1284
1285       g_set_error (error,
1286                    G_FILE_ERROR,
1287                    G_FILE_ERROR_FAILED,
1288                    _("Template '%s' invalid, should not contain a '%s'"),
1289                    display_tmpl, c);
1290       g_free (display_tmpl);
1291
1292       return -1;
1293     }
1294   
1295   if (strlen (tmpl) < 6 ||
1296       strcmp (tmpl + strlen (tmpl) - 6, "XXXXXX") != 0)
1297     {
1298       gchar *display_tmpl = g_filename_display_name (tmpl);
1299       g_set_error (error,
1300                    G_FILE_ERROR,
1301                    G_FILE_ERROR_FAILED,
1302                    _("Template '%s' doesn't end with XXXXXX"),
1303                    display_tmpl);
1304       g_free (display_tmpl);
1305       return -1;
1306     }
1307
1308   tmpdir = g_get_tmp_dir ();
1309
1310   if (G_IS_DIR_SEPARATOR (tmpdir [strlen (tmpdir) - 1]))
1311     sep = "";
1312   else
1313     sep = G_DIR_SEPARATOR_S;
1314
1315   fulltemplate = g_strconcat (tmpdir, sep, tmpl, NULL);
1316
1317   retval = g_mkstemp (fulltemplate);
1318
1319   if (retval == -1)
1320     {
1321       int save_errno = errno;
1322       gchar *display_fulltemplate = g_filename_display_name (fulltemplate);
1323
1324       g_set_error (error,
1325                    G_FILE_ERROR,
1326                    g_file_error_from_errno (save_errno),
1327                    _("Failed to create file '%s': %s"),
1328                    display_fulltemplate, g_strerror (save_errno));
1329       g_free (display_fulltemplate);
1330       g_free (fulltemplate);
1331       return -1;
1332     }
1333
1334   if (name_used)
1335     *name_used = fulltemplate;
1336   else
1337     g_free (fulltemplate);
1338
1339   return retval;
1340 }
1341
1342 #ifdef G_OS_WIN32
1343
1344 #undef g_file_open_tmp
1345
1346 /* Binary compatibility version. Not for newly compiled code. */
1347
1348 gint
1349 g_file_open_tmp (const gchar *tmpl,
1350                  gchar      **name_used,
1351                  GError     **error)
1352 {
1353   gchar *utf8_tmpl = g_locale_to_utf8 (tmpl, -1, NULL, NULL, error);
1354   gchar *utf8_name_used;
1355   gint retval;
1356
1357   if (utf8_tmpl == NULL)
1358     return -1;
1359
1360   retval = g_file_open_tmp_utf8 (utf8_tmpl, &utf8_name_used, error);
1361   
1362   if (retval == -1)
1363     return -1;
1364
1365   if (name_used)
1366     *name_used = g_locale_from_utf8 (utf8_name_used, -1, NULL, NULL, NULL);
1367
1368   g_free (utf8_name_used);
1369
1370   return retval;
1371 }
1372
1373 #endif
1374
1375 static gchar *
1376 g_build_pathv (const gchar *separator,
1377                const gchar *first_element,
1378                va_list      args)
1379 {
1380   GString *result;
1381   gint separator_len = strlen (separator);
1382   gboolean is_first = TRUE;
1383   gboolean have_leading = FALSE;
1384   const gchar *single_element = NULL;
1385   const gchar *next_element;
1386   const gchar *last_trailing = NULL;
1387
1388   result = g_string_new (NULL);
1389
1390   next_element = first_element;
1391
1392   while (TRUE)
1393     {
1394       const gchar *element;
1395       const gchar *start;
1396       const gchar *end;
1397
1398       if (next_element)
1399         {
1400           element = next_element;
1401           next_element = va_arg (args, gchar *);
1402         }
1403       else
1404         break;
1405
1406       /* Ignore empty elements */
1407       if (!*element)
1408         continue;
1409       
1410       start = element;
1411
1412       if (separator_len)
1413         {
1414           while (start &&
1415                  strncmp (start, separator, separator_len) == 0)
1416             start += separator_len;
1417         }
1418
1419       end = start + strlen (start);
1420       
1421       if (separator_len)
1422         {
1423           while (end >= start + separator_len &&
1424                  strncmp (end - separator_len, separator, separator_len) == 0)
1425             end -= separator_len;
1426           
1427           last_trailing = end;
1428           while (last_trailing >= element + separator_len &&
1429                  strncmp (last_trailing - separator_len, separator, separator_len) == 0)
1430             last_trailing -= separator_len;
1431
1432           if (!have_leading)
1433             {
1434               /* If the leading and trailing separator strings are in the
1435                * same element and overlap, the result is exactly that element
1436                */
1437               if (last_trailing <= start)
1438                 single_element = element;
1439                   
1440               g_string_append_len (result, element, start - element);
1441               have_leading = TRUE;
1442             }
1443           else
1444             single_element = NULL;
1445         }
1446
1447       if (end == start)
1448         continue;
1449
1450       if (!is_first)
1451         g_string_append (result, separator);
1452       
1453       g_string_append_len (result, start, end - start);
1454       is_first = FALSE;
1455     }
1456
1457   if (single_element)
1458     {
1459       g_string_free (result, TRUE);
1460       return g_strdup (single_element);
1461     }
1462   else
1463     {
1464       if (last_trailing)
1465         g_string_append (result, last_trailing);
1466   
1467       return g_string_free (result, FALSE);
1468     }
1469 }
1470
1471 /**
1472  * g_build_path:
1473  * @separator: a string used to separator the elements of the path.
1474  * @first_element: the first element in the path
1475  * @Varargs: remaining elements in path, terminated by %NULL
1476  * 
1477  * Creates a path from a series of elements using @separator as the
1478  * separator between elements. At the boundary between two elements,
1479  * any trailing occurrences of separator in the first element, or
1480  * leading occurrences of separator in the second element are removed
1481  * and exactly one copy of the separator is inserted.
1482  *
1483  * Empty elements are ignored.
1484  *
1485  * The number of leading copies of the separator on the result is
1486  * the same as the number of leading copies of the separator on
1487  * the first non-empty element.
1488  *
1489  * The number of trailing copies of the separator on the result is
1490  * the same as the number of trailing copies of the separator on
1491  * the last non-empty element. (Determination of the number of
1492  * trailing copies is done without stripping leading copies, so
1493  * if the separator is <literal>ABA</literal>, <literal>ABABA</literal>
1494  * has 1 trailing copy.)
1495  *
1496  * However, if there is only a single non-empty element, and there
1497  * are no characters in that element not part of the leading or
1498  * trailing separators, then the result is exactly the original value
1499  * of that element.
1500  *
1501  * Other than for determination of the number of leading and trailing
1502  * copies of the separator, elements consisting only of copies
1503  * of the separator are ignored.
1504  * 
1505  * Return value: a newly-allocated string that must be freed with g_free().
1506  **/
1507 gchar *
1508 g_build_path (const gchar *separator,
1509               const gchar *first_element,
1510               ...)
1511 {
1512   gchar *str;
1513   va_list args;
1514
1515   g_return_val_if_fail (separator != NULL, NULL);
1516
1517   va_start (args, first_element);
1518   str = g_build_pathv (separator, first_element, args);
1519   va_end (args);
1520
1521   return str;
1522 }
1523
1524 /**
1525  * g_build_filename:
1526  * @first_element: the first element in the path
1527  * @Varargs: remaining elements in path, terminated by %NULL
1528  * 
1529  * Creates a filename from a series of elements using the correct
1530  * separator for filenames.
1531  *
1532  * On Unix, this function behaves identically to <literal>g_build_path
1533  * (G_DIR_SEPARATOR_S, first_element, ....)</literal>.
1534  *
1535  * On Windows, it takes into account that either the backslash
1536  * (<literal>\</literal> or slash (<literal>/</literal>) can be used
1537  * as separator in filenames, but otherwise behaves as on Unix. When
1538  * file pathname separators need to be inserted, the one that last
1539  * previously occurred in the parameters (reading from left to right)
1540  * is used.
1541  *
1542  * No attempt is made to force the resulting filename to be an absolute
1543  * path. If the first element is a relative path, the result will
1544  * be a relative path. 
1545  * 
1546  * Return value: a newly-allocated string that must be freed with g_free().
1547  **/
1548 gchar *
1549 g_build_filename (const gchar *first_element, 
1550                   ...)
1551 {
1552 #ifndef G_OS_WIN32
1553   gchar *str;
1554   va_list args;
1555
1556   va_start (args, first_element);
1557   str = g_build_pathv (G_DIR_SEPARATOR_S, first_element, args);
1558   va_end (args);
1559
1560   return str;
1561 #else
1562   /* Code copied from g_build_pathv(), and modifed to use two
1563    * alternative single-character separators.
1564    */
1565   va_list args;
1566   GString *result;
1567   gboolean is_first = TRUE;
1568   gboolean have_leading = FALSE;
1569   const gchar *single_element = NULL;
1570   const gchar *next_element;
1571   const gchar *last_trailing = NULL;
1572   gchar current_separator = '\\';
1573
1574   va_start (args, first_element);
1575
1576   result = g_string_new (NULL);
1577
1578   next_element = first_element;
1579
1580   while (TRUE)
1581     {
1582       const gchar *element;
1583       const gchar *start;
1584       const gchar *end;
1585
1586       if (next_element)
1587         {
1588           element = next_element;
1589           next_element = va_arg (args, gchar *);
1590         }
1591       else
1592         break;
1593
1594       /* Ignore empty elements */
1595       if (!*element)
1596         continue;
1597       
1598       start = element;
1599
1600       if (TRUE)
1601         {
1602           while (start &&
1603                  (*start == '\\' || *start == '/'))
1604             {
1605               current_separator = *start;
1606               start++;
1607             }
1608         }
1609
1610       end = start + strlen (start);
1611       
1612       if (TRUE)
1613         {
1614           while (end >= start + 1 &&
1615                  (end[-1] == '\\' || end[-1] == '/'))
1616             {
1617               current_separator = end[-1];
1618               end--;
1619             }
1620           
1621           last_trailing = end;
1622           while (last_trailing >= element + 1 &&
1623                  (last_trailing[-1] == '\\' || last_trailing[-1] == '/'))
1624             last_trailing--;
1625
1626           if (!have_leading)
1627             {
1628               /* If the leading and trailing separator strings are in the
1629                * same element and overlap, the result is exactly that element
1630                */
1631               if (last_trailing <= start)
1632                 single_element = element;
1633                   
1634               g_string_append_len (result, element, start - element);
1635               have_leading = TRUE;
1636             }
1637           else
1638             single_element = NULL;
1639         }
1640
1641       if (end == start)
1642         continue;
1643
1644       if (!is_first)
1645         g_string_append_len (result, &current_separator, 1);
1646       
1647       g_string_append_len (result, start, end - start);
1648       is_first = FALSE;
1649     }
1650
1651   va_end (args);
1652
1653   if (single_element)
1654     {
1655       g_string_free (result, TRUE);
1656       return g_strdup (single_element);
1657     }
1658   else
1659     {
1660       if (last_trailing)
1661         g_string_append (result, last_trailing);
1662   
1663       return g_string_free (result, FALSE);
1664     }
1665 #endif
1666 }
1667
1668 /**
1669  * g_file_read_link:
1670  * @filename: the symbolic link
1671  * @error: return location for a #GError
1672  *
1673  * Reads the contents of the symbolic link @filename like the POSIX
1674  * readlink() function.  The returned string is in the encoding used
1675  * for filenames. Use g_filename_to_utf8() to convert it to UTF-8.
1676  *
1677  * Returns: A newly allocated string with the contents of the symbolic link, 
1678  *          or %NULL if an error occurred.
1679  *
1680  * Since: 2.4
1681  */
1682 gchar *
1683 g_file_read_link (const gchar *filename,
1684                   GError     **error)
1685 {
1686 #ifdef HAVE_READLINK
1687   gchar *buffer;
1688   guint size;
1689   gint read_size;    
1690   
1691   size = 256; 
1692   buffer = g_malloc (size);
1693   
1694   while (TRUE) 
1695     {
1696       read_size = readlink (filename, buffer, size);
1697       if (read_size < 0) {
1698         int save_errno = errno;
1699         gchar *display_filename = g_filename_display_name (filename);
1700
1701         g_free (buffer);
1702         g_set_error (error,
1703                      G_FILE_ERROR,
1704                      g_file_error_from_errno (save_errno),
1705                      _("Failed to read the symbolic link '%s': %s"),
1706                      display_filename, 
1707                      g_strerror (save_errno));
1708         g_free (display_filename);
1709         
1710         return NULL;
1711       }
1712     
1713       if (read_size < size) 
1714         {
1715           buffer[read_size] = 0;
1716           return buffer;
1717         }
1718       
1719       size *= 2;
1720       buffer = g_realloc (buffer, size);
1721     }
1722 #else
1723   g_set_error (error,
1724                G_FILE_ERROR,
1725                G_FILE_ERROR_INVAL,
1726                _("Symbolic links not supported"));
1727         
1728   return NULL;
1729 #endif
1730 }
1731
1732 #define __G_FILEUTILS_C__
1733 #include "galiasdef.c"