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