(Ffind_file_name_handler): Handle the `operations'
[bpt/emacs.git] / src / fileio.c
1 /* File IO for GNU Emacs.
2 Copyright (C) 1985, 1986, 1987, 1988, 1993, 1994, 1995, 1996, 1997, 1998,
3 1999, 2000, 2001, 2003, 2004, 2005 Free Software Foundation, Inc.
4
5 This file is part of GNU Emacs.
6
7 GNU Emacs is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2, or (at your option)
10 any later version.
11
12 GNU Emacs is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with GNU Emacs; see the file COPYING. If not, write to
19 the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
20 Boston, MA 02111-1307, USA. */
21
22 #include <config.h>
23
24 #ifdef HAVE_FCNTL_H
25 #include <fcntl.h>
26 #endif
27
28 #include <stdio.h>
29 #include <sys/types.h>
30 #include <sys/stat.h>
31
32 #ifdef HAVE_UNISTD_H
33 #include <unistd.h>
34 #endif
35
36 #if !defined (S_ISLNK) && defined (S_IFLNK)
37 # define S_ISLNK(m) (((m) & S_IFMT) == S_IFLNK)
38 #endif
39
40 #if !defined (S_ISFIFO) && defined (S_IFIFO)
41 # define S_ISFIFO(m) (((m) & S_IFMT) == S_IFIFO)
42 #endif
43
44 #if !defined (S_ISREG) && defined (S_IFREG)
45 # define S_ISREG(m) (((m) & S_IFMT) == S_IFREG)
46 #endif
47
48 #ifdef HAVE_PWD_H
49 #include <pwd.h>
50 #endif
51
52 #include <ctype.h>
53
54 #ifdef VMS
55 #include "vmsdir.h"
56 #include <perror.h>
57 #include <stddef.h>
58 #include <string.h>
59 #endif
60
61 #include <errno.h>
62
63 #ifndef vax11c
64 #ifndef USE_CRT_DLL
65 extern int errno;
66 #endif
67 #endif
68
69 #ifdef APOLLO
70 #include <sys/time.h>
71 #endif
72
73 #include "lisp.h"
74 #include "intervals.h"
75 #include "buffer.h"
76 #include "charset.h"
77 #include "coding.h"
78 #include "window.h"
79
80 #ifdef WINDOWSNT
81 #define NOMINMAX 1
82 #include <windows.h>
83 #include <stdlib.h>
84 #include <fcntl.h>
85 #endif /* not WINDOWSNT */
86
87 #ifdef MSDOS
88 #include "msdos.h"
89 #include <sys/param.h>
90 #if __DJGPP__ >= 2
91 #include <fcntl.h>
92 #include <string.h>
93 #endif
94 #endif
95
96 #ifdef DOS_NT
97 #define CORRECT_DIR_SEPS(s) \
98 do { if ('/' == DIRECTORY_SEP) dostounix_filename (s); \
99 else unixtodos_filename (s); \
100 } while (0)
101 /* On Windows, drive letters must be alphabetic - on DOS, the Netware
102 redirector allows the six letters between 'Z' and 'a' as well. */
103 #ifdef MSDOS
104 #define IS_DRIVE(x) ((x) >= 'A' && (x) <= 'z')
105 #endif
106 #ifdef WINDOWSNT
107 #define IS_DRIVE(x) isalpha (x)
108 #endif
109 /* Need to lower-case the drive letter, or else expanded
110 filenames will sometimes compare inequal, because
111 `expand-file-name' doesn't always down-case the drive letter. */
112 #define DRIVE_LETTER(x) (tolower (x))
113 #endif
114
115 #ifdef VMS
116 #include <file.h>
117 #include <rmsdef.h>
118 #include <fab.h>
119 #include <nam.h>
120 #endif
121
122 #include "systime.h"
123
124 #ifdef HPUX
125 #include <netio.h>
126 #ifndef HPUX8
127 #ifndef HPUX9
128 #include <errnet.h>
129 #endif
130 #endif
131 #endif
132
133 #include "commands.h"
134 extern int use_dialog_box;
135 extern int use_file_dialog;
136
137 #ifndef O_WRONLY
138 #define O_WRONLY 1
139 #endif
140
141 #ifndef O_RDONLY
142 #define O_RDONLY 0
143 #endif
144
145 #ifndef S_ISLNK
146 # define lstat stat
147 #endif
148
149 #ifndef FILE_SYSTEM_CASE
150 #define FILE_SYSTEM_CASE(filename) (filename)
151 #endif
152
153 /* Nonzero during writing of auto-save files */
154 int auto_saving;
155
156 /* Set by auto_save_1 to mode of original file so Fwrite_region will create
157 a new file with the same mode as the original */
158 int auto_save_mode_bits;
159
160 /* The symbol bound to coding-system-for-read when
161 insert-file-contents is called for recovering a file. This is not
162 an actual coding system name, but just an indicator to tell
163 insert-file-contents to use `emacs-mule' with a special flag for
164 auto saving and recovering a file. */
165 Lisp_Object Qauto_save_coding;
166
167 /* Coding system for file names, or nil if none. */
168 Lisp_Object Vfile_name_coding_system;
169
170 /* Coding system for file names used only when
171 Vfile_name_coding_system is nil. */
172 Lisp_Object Vdefault_file_name_coding_system;
173
174 /* Alist of elements (REGEXP . HANDLER) for file names
175 whose I/O is done with a special handler. */
176 Lisp_Object Vfile_name_handler_alist;
177
178 /* Property name of a file name handler,
179 which gives a list of operations it handles.. */
180 Lisp_Object Qoperations;
181
182 /* Lisp functions for translating file formats */
183 Lisp_Object Qformat_decode, Qformat_annotate_function;
184
185 /* Function to be called to decide a coding system of a reading file. */
186 Lisp_Object Vset_auto_coding_function;
187
188 /* Functions to be called to process text properties in inserted file. */
189 Lisp_Object Vafter_insert_file_functions;
190
191 /* Lisp function for setting buffer-file-coding-system and the
192 multibyteness of the current buffer after inserting a file. */
193 Lisp_Object Qafter_insert_file_set_coding;
194
195 /* Functions to be called to create text property annotations for file. */
196 Lisp_Object Vwrite_region_annotate_functions;
197 Lisp_Object Qwrite_region_annotate_functions;
198
199 /* During build_annotations, each time an annotation function is called,
200 this holds the annotations made by the previous functions. */
201 Lisp_Object Vwrite_region_annotations_so_far;
202
203 /* File name in which we write a list of all our auto save files. */
204 Lisp_Object Vauto_save_list_file_name;
205
206 /* Function to call to read a file name. */
207 Lisp_Object Vread_file_name_function;
208
209 /* Current predicate used by read_file_name_internal. */
210 Lisp_Object Vread_file_name_predicate;
211
212 /* Nonzero means completion ignores case when reading file name. */
213 int read_file_name_completion_ignore_case;
214
215 /* Nonzero means, when reading a filename in the minibuffer,
216 start out by inserting the default directory into the minibuffer. */
217 int insert_default_directory;
218
219 /* On VMS, nonzero means write new files with record format stmlf.
220 Zero means use var format. */
221 int vms_stmlf_recfm;
222
223 /* On NT, specifies the directory separator character, used (eg.) when
224 expanding file names. This can be bound to / or \. */
225 Lisp_Object Vdirectory_sep_char;
226
227 extern Lisp_Object Vuser_login_name;
228
229 #ifdef WINDOWSNT
230 extern Lisp_Object Vw32_get_true_file_attributes;
231 #endif
232
233 extern int minibuf_level;
234
235 extern int minibuffer_auto_raise;
236
237 extern int history_delete_duplicates;
238
239 /* These variables describe handlers that have "already" had a chance
240 to handle the current operation.
241
242 Vinhibit_file_name_handlers is a list of file name handlers.
243 Vinhibit_file_name_operation is the operation being handled.
244 If we try to handle that operation, we ignore those handlers. */
245
246 static Lisp_Object Vinhibit_file_name_handlers;
247 static Lisp_Object Vinhibit_file_name_operation;
248
249 Lisp_Object Qfile_error, Qfile_already_exists, Qfile_date_error;
250 Lisp_Object Qexcl;
251 Lisp_Object Qfile_name_history;
252
253 Lisp_Object Qcar_less_than_car;
254
255 static int a_write P_ ((int, Lisp_Object, int, int,
256 Lisp_Object *, struct coding_system *));
257 static int e_write P_ ((int, Lisp_Object, int, int, struct coding_system *));
258
259 \f
260 void
261 report_file_error (string, data)
262 const char *string;
263 Lisp_Object data;
264 {
265 Lisp_Object errstring;
266 int errorno = errno;
267
268 synchronize_system_messages_locale ();
269 errstring = code_convert_string_norecord (build_string (strerror (errorno)),
270 Vlocale_coding_system, 0);
271
272 while (1)
273 switch (errorno)
274 {
275 case EEXIST:
276 Fsignal (Qfile_already_exists, Fcons (errstring, data));
277 break;
278 default:
279 /* System error messages are capitalized. Downcase the initial
280 unless it is followed by a slash. */
281 if (SREF (errstring, 1) != '/')
282 SSET (errstring, 0, DOWNCASE (SREF (errstring, 0)));
283
284 Fsignal (Qfile_error,
285 Fcons (build_string (string), Fcons (errstring, data)));
286 }
287 }
288
289 Lisp_Object
290 close_file_unwind (fd)
291 Lisp_Object fd;
292 {
293 emacs_close (XFASTINT (fd));
294 return Qnil;
295 }
296
297 /* Restore point, having saved it as a marker. */
298
299 static Lisp_Object
300 restore_point_unwind (location)
301 Lisp_Object location;
302 {
303 Fgoto_char (location);
304 Fset_marker (location, Qnil, Qnil);
305 return Qnil;
306 }
307 \f
308 Lisp_Object Qexpand_file_name;
309 Lisp_Object Qsubstitute_in_file_name;
310 Lisp_Object Qdirectory_file_name;
311 Lisp_Object Qfile_name_directory;
312 Lisp_Object Qfile_name_nondirectory;
313 Lisp_Object Qunhandled_file_name_directory;
314 Lisp_Object Qfile_name_as_directory;
315 Lisp_Object Qcopy_file;
316 Lisp_Object Qmake_directory_internal;
317 Lisp_Object Qmake_directory;
318 Lisp_Object Qdelete_directory;
319 Lisp_Object Qdelete_file;
320 Lisp_Object Qrename_file;
321 Lisp_Object Qadd_name_to_file;
322 Lisp_Object Qmake_symbolic_link;
323 Lisp_Object Qfile_exists_p;
324 Lisp_Object Qfile_executable_p;
325 Lisp_Object Qfile_readable_p;
326 Lisp_Object Qfile_writable_p;
327 Lisp_Object Qfile_symlink_p;
328 Lisp_Object Qaccess_file;
329 Lisp_Object Qfile_directory_p;
330 Lisp_Object Qfile_regular_p;
331 Lisp_Object Qfile_accessible_directory_p;
332 Lisp_Object Qfile_modes;
333 Lisp_Object Qset_file_modes;
334 Lisp_Object Qset_file_times;
335 Lisp_Object Qfile_newer_than_file_p;
336 Lisp_Object Qinsert_file_contents;
337 Lisp_Object Qwrite_region;
338 Lisp_Object Qverify_visited_file_modtime;
339 Lisp_Object Qset_visited_file_modtime;
340
341 DEFUN ("find-file-name-handler", Ffind_file_name_handler, Sfind_file_name_handler, 2, 2, 0,
342 doc: /* Return FILENAME's handler function for OPERATION, if it has one.
343 Otherwise, return nil.
344 A file name is handled if one of the regular expressions in
345 `file-name-handler-alist' matches it.
346
347 If OPERATION equals `inhibit-file-name-operation', then we ignore
348 any handlers that are members of `inhibit-file-name-handlers',
349 but we still do run any other handlers. This lets handlers
350 use the standard functions without calling themselves recursively. */)
351 (filename, operation)
352 Lisp_Object filename, operation;
353 {
354 /* This function must not munge the match data. */
355 Lisp_Object chain, inhibited_handlers, result;
356 int pos = -1;
357
358 result = Qnil;
359 CHECK_STRING (filename);
360
361 if (EQ (operation, Vinhibit_file_name_operation))
362 inhibited_handlers = Vinhibit_file_name_handlers;
363 else
364 inhibited_handlers = Qnil;
365
366 for (chain = Vfile_name_handler_alist; CONSP (chain);
367 chain = XCDR (chain))
368 {
369 Lisp_Object elt;
370 elt = XCAR (chain);
371 if (CONSP (elt))
372 {
373 Lisp_Object string = XCAR (elt);
374 int match_pos;
375 Lisp_Object handler = XCDR (elt);
376 Lisp_Object operations = Fget (handler, Qoperations);
377
378 if (STRINGP (string)
379 && (match_pos = fast_string_match (string, filename)) > pos
380 && (NILP (operations) || ! NILP (Fmemq (operation, operations))))
381 {
382 Lisp_Object tem;
383
384 handler = XCDR (elt);
385 tem = Fmemq (handler, inhibited_handlers);
386 if (NILP (tem))
387 {
388 result = handler;
389 pos = match_pos;
390 }
391 }
392 }
393
394 QUIT;
395 }
396 return result;
397 }
398 \f
399 DEFUN ("file-name-directory", Ffile_name_directory, Sfile_name_directory,
400 1, 1, 0,
401 doc: /* Return the directory component in file name FILENAME.
402 Return nil if FILENAME does not include a directory.
403 Otherwise return a directory spec.
404 Given a Unix syntax file name, returns a string ending in slash;
405 on VMS, perhaps instead a string ending in `:', `]' or `>'. */)
406 (filename)
407 Lisp_Object filename;
408 {
409 #ifndef DOS_NT
410 register const unsigned char *beg;
411 #else
412 register unsigned char *beg;
413 #endif
414 register const unsigned char *p;
415 Lisp_Object handler;
416
417 CHECK_STRING (filename);
418
419 /* If the file name has special constructs in it,
420 call the corresponding file handler. */
421 handler = Ffind_file_name_handler (filename, Qfile_name_directory);
422 if (!NILP (handler))
423 return call2 (handler, Qfile_name_directory, filename);
424
425 filename = FILE_SYSTEM_CASE (filename);
426 beg = SDATA (filename);
427 #ifdef DOS_NT
428 beg = strcpy (alloca (strlen (beg) + 1), beg);
429 #endif
430 p = beg + SBYTES (filename);
431
432 while (p != beg && !IS_DIRECTORY_SEP (p[-1])
433 #ifdef VMS
434 && p[-1] != ':' && p[-1] != ']' && p[-1] != '>'
435 #endif /* VMS */
436 #ifdef DOS_NT
437 /* only recognise drive specifier at the beginning */
438 && !(p[-1] == ':'
439 /* handle the "/:d:foo" and "/:foo" cases correctly */
440 && ((p == beg + 2 && !IS_DIRECTORY_SEP (*beg))
441 || (p == beg + 4 && IS_DIRECTORY_SEP (*beg))))
442 #endif
443 ) p--;
444
445 if (p == beg)
446 return Qnil;
447 #ifdef DOS_NT
448 /* Expansion of "c:" to drive and default directory. */
449 if (p[-1] == ':')
450 {
451 /* MAXPATHLEN+1 is guaranteed to be enough space for getdefdir. */
452 unsigned char *res = alloca (MAXPATHLEN + 1);
453 unsigned char *r = res;
454
455 if (p == beg + 4 && IS_DIRECTORY_SEP (*beg) && beg[1] == ':')
456 {
457 strncpy (res, beg, 2);
458 beg += 2;
459 r += 2;
460 }
461
462 if (getdefdir (toupper (*beg) - 'A' + 1, r))
463 {
464 if (!IS_DIRECTORY_SEP (res[strlen (res) - 1]))
465 strcat (res, "/");
466 beg = res;
467 p = beg + strlen (beg);
468 }
469 }
470 CORRECT_DIR_SEPS (beg);
471 #endif /* DOS_NT */
472
473 return make_specified_string (beg, -1, p - beg, STRING_MULTIBYTE (filename));
474 }
475
476 DEFUN ("file-name-nondirectory", Ffile_name_nondirectory,
477 Sfile_name_nondirectory, 1, 1, 0,
478 doc: /* Return file name FILENAME sans its directory.
479 For example, in a Unix-syntax file name,
480 this is everything after the last slash,
481 or the entire name if it contains no slash. */)
482 (filename)
483 Lisp_Object filename;
484 {
485 register const unsigned char *beg, *p, *end;
486 Lisp_Object handler;
487
488 CHECK_STRING (filename);
489
490 /* If the file name has special constructs in it,
491 call the corresponding file handler. */
492 handler = Ffind_file_name_handler (filename, Qfile_name_nondirectory);
493 if (!NILP (handler))
494 return call2 (handler, Qfile_name_nondirectory, filename);
495
496 beg = SDATA (filename);
497 end = p = beg + SBYTES (filename);
498
499 while (p != beg && !IS_DIRECTORY_SEP (p[-1])
500 #ifdef VMS
501 && p[-1] != ':' && p[-1] != ']' && p[-1] != '>'
502 #endif /* VMS */
503 #ifdef DOS_NT
504 /* only recognise drive specifier at beginning */
505 && !(p[-1] == ':'
506 /* handle the "/:d:foo" case correctly */
507 && (p == beg + 2 || (p == beg + 4 && IS_DIRECTORY_SEP (*beg))))
508 #endif
509 )
510 p--;
511
512 return make_specified_string (p, -1, end - p, STRING_MULTIBYTE (filename));
513 }
514
515 DEFUN ("unhandled-file-name-directory", Funhandled_file_name_directory,
516 Sunhandled_file_name_directory, 1, 1, 0,
517 doc: /* Return a directly usable directory name somehow associated with FILENAME.
518 A `directly usable' directory name is one that may be used without the
519 intervention of any file handler.
520 If FILENAME is a directly usable file itself, return
521 \(file-name-directory FILENAME).
522 The `call-process' and `start-process' functions use this function to
523 get a current directory to run processes in. */)
524 (filename)
525 Lisp_Object filename;
526 {
527 Lisp_Object handler;
528
529 /* If the file name has special constructs in it,
530 call the corresponding file handler. */
531 handler = Ffind_file_name_handler (filename, Qunhandled_file_name_directory);
532 if (!NILP (handler))
533 return call2 (handler, Qunhandled_file_name_directory, filename);
534
535 return Ffile_name_directory (filename);
536 }
537
538 \f
539 char *
540 file_name_as_directory (out, in)
541 char *out, *in;
542 {
543 int size = strlen (in) - 1;
544
545 strcpy (out, in);
546
547 if (size < 0)
548 {
549 out[0] = '.';
550 out[1] = '/';
551 out[2] = 0;
552 return out;
553 }
554
555 #ifdef VMS
556 /* Is it already a directory string? */
557 if (in[size] == ':' || in[size] == ']' || in[size] == '>')
558 return out;
559 /* Is it a VMS directory file name? If so, hack VMS syntax. */
560 else if (! index (in, '/')
561 && ((size > 3 && ! strcmp (&in[size - 3], ".DIR"))
562 || (size > 3 && ! strcmp (&in[size - 3], ".dir"))
563 || (size > 5 && (! strncmp (&in[size - 5], ".DIR", 4)
564 || ! strncmp (&in[size - 5], ".dir", 4))
565 && (in[size - 1] == '.' || in[size - 1] == ';')
566 && in[size] == '1')))
567 {
568 register char *p, *dot;
569 char brack;
570
571 /* x.dir -> [.x]
572 dir:x.dir --> dir:[x]
573 dir:[x]y.dir --> dir:[x.y] */
574 p = in + size;
575 while (p != in && *p != ':' && *p != '>' && *p != ']') p--;
576 if (p != in)
577 {
578 strncpy (out, in, p - in);
579 out[p - in] = '\0';
580 if (*p == ':')
581 {
582 brack = ']';
583 strcat (out, ":[");
584 }
585 else
586 {
587 brack = *p;
588 strcat (out, ".");
589 }
590 p++;
591 }
592 else
593 {
594 brack = ']';
595 strcpy (out, "[.");
596 }
597 dot = index (p, '.');
598 if (dot)
599 {
600 /* blindly remove any extension */
601 size = strlen (out) + (dot - p);
602 strncat (out, p, dot - p);
603 }
604 else
605 {
606 strcat (out, p);
607 size = strlen (out);
608 }
609 out[size++] = brack;
610 out[size] = '\0';
611 }
612 #else /* not VMS */
613 /* For Unix syntax, Append a slash if necessary */
614 if (!IS_DIRECTORY_SEP (out[size]))
615 {
616 /* Cannot use DIRECTORY_SEP, which could have any value */
617 out[size + 1] = '/';
618 out[size + 2] = '\0';
619 }
620 #ifdef DOS_NT
621 CORRECT_DIR_SEPS (out);
622 #endif
623 #endif /* not VMS */
624 return out;
625 }
626
627 DEFUN ("file-name-as-directory", Ffile_name_as_directory,
628 Sfile_name_as_directory, 1, 1, 0,
629 doc: /* Return a string representing the file name FILE interpreted as a directory.
630 This operation exists because a directory is also a file, but its name as
631 a directory is different from its name as a file.
632 The result can be used as the value of `default-directory'
633 or passed as second argument to `expand-file-name'.
634 For a Unix-syntax file name, just appends a slash.
635 On VMS, converts \"[X]FOO.DIR\" to \"[X.FOO]\", etc. */)
636 (file)
637 Lisp_Object file;
638 {
639 char *buf;
640 Lisp_Object handler;
641
642 CHECK_STRING (file);
643 if (NILP (file))
644 return Qnil;
645
646 /* If the file name has special constructs in it,
647 call the corresponding file handler. */
648 handler = Ffind_file_name_handler (file, Qfile_name_as_directory);
649 if (!NILP (handler))
650 return call2 (handler, Qfile_name_as_directory, file);
651
652 buf = (char *) alloca (SBYTES (file) + 10);
653 file_name_as_directory (buf, SDATA (file));
654 return make_specified_string (buf, -1, strlen (buf),
655 STRING_MULTIBYTE (file));
656 }
657 \f
658 /*
659 * Convert from directory name to filename.
660 * On VMS:
661 * xyzzy:[mukesh.emacs] => xyzzy:[mukesh]emacs.dir.1
662 * xyzzy:[mukesh] => xyzzy:[000000]mukesh.dir.1
663 * On UNIX, it's simple: just make sure there isn't a terminating /
664
665 * Value is nonzero if the string output is different from the input.
666 */
667
668 int
669 directory_file_name (src, dst)
670 char *src, *dst;
671 {
672 long slen;
673 #ifdef VMS
674 long rlen;
675 char * ptr, * rptr;
676 char bracket;
677 struct FAB fab = cc$rms_fab;
678 struct NAM nam = cc$rms_nam;
679 char esa[NAM$C_MAXRSS];
680 #endif /* VMS */
681
682 slen = strlen (src);
683 #ifdef VMS
684 if (! index (src, '/')
685 && (src[slen - 1] == ']'
686 || src[slen - 1] == ':'
687 || src[slen - 1] == '>'))
688 {
689 /* VMS style - convert [x.y.z] to [x.y]z, [x] to [000000]x */
690 fab.fab$l_fna = src;
691 fab.fab$b_fns = slen;
692 fab.fab$l_nam = &nam;
693 fab.fab$l_fop = FAB$M_NAM;
694
695 nam.nam$l_esa = esa;
696 nam.nam$b_ess = sizeof esa;
697 nam.nam$b_nop |= NAM$M_SYNCHK;
698
699 /* We call SYS$PARSE to handle such things as [--] for us. */
700 if (SYS$PARSE (&fab, 0, 0) == RMS$_NORMAL)
701 {
702 slen = nam.nam$b_esl;
703 if (esa[slen - 1] == ';' && esa[slen - 2] == '.')
704 slen -= 2;
705 esa[slen] = '\0';
706 src = esa;
707 }
708 if (src[slen - 1] != ']' && src[slen - 1] != '>')
709 {
710 /* what about when we have logical_name:???? */
711 if (src[slen - 1] == ':')
712 { /* Xlate logical name and see what we get */
713 ptr = strcpy (dst, src); /* upper case for getenv */
714 while (*ptr)
715 {
716 if ('a' <= *ptr && *ptr <= 'z')
717 *ptr -= 040;
718 ptr++;
719 }
720 dst[slen - 1] = 0; /* remove colon */
721 if (!(src = egetenv (dst)))
722 return 0;
723 /* should we jump to the beginning of this procedure?
724 Good points: allows us to use logical names that xlate
725 to Unix names,
726 Bad points: can be a problem if we just translated to a device
727 name...
728 For now, I'll punt and always expect VMS names, and hope for
729 the best! */
730 slen = strlen (src);
731 if (src[slen - 1] != ']' && src[slen - 1] != '>')
732 { /* no recursion here! */
733 strcpy (dst, src);
734 return 0;
735 }
736 }
737 else
738 { /* not a directory spec */
739 strcpy (dst, src);
740 return 0;
741 }
742 }
743 bracket = src[slen - 1];
744
745 /* If bracket is ']' or '>', bracket - 2 is the corresponding
746 opening bracket. */
747 ptr = index (src, bracket - 2);
748 if (ptr == 0)
749 { /* no opening bracket */
750 strcpy (dst, src);
751 return 0;
752 }
753 if (!(rptr = rindex (src, '.')))
754 rptr = ptr;
755 slen = rptr - src;
756 strncpy (dst, src, slen);
757 dst[slen] = '\0';
758 if (*rptr == '.')
759 {
760 dst[slen++] = bracket;
761 dst[slen] = '\0';
762 }
763 else
764 {
765 /* If we have the top-level of a rooted directory (i.e. xx:[000000]),
766 then translate the device and recurse. */
767 if (dst[slen - 1] == ':'
768 && dst[slen - 2] != ':' /* skip decnet nodes */
769 && strcmp (src + slen, "[000000]") == 0)
770 {
771 dst[slen - 1] = '\0';
772 if ((ptr = egetenv (dst))
773 && (rlen = strlen (ptr) - 1) > 0
774 && (ptr[rlen] == ']' || ptr[rlen] == '>')
775 && ptr[rlen - 1] == '.')
776 {
777 char * buf = (char *) alloca (strlen (ptr) + 1);
778 strcpy (buf, ptr);
779 buf[rlen - 1] = ']';
780 buf[rlen] = '\0';
781 return directory_file_name (buf, dst);
782 }
783 else
784 dst[slen - 1] = ':';
785 }
786 strcat (dst, "[000000]");
787 slen += 8;
788 }
789 rptr++;
790 rlen = strlen (rptr) - 1;
791 strncat (dst, rptr, rlen);
792 dst[slen + rlen] = '\0';
793 strcat (dst, ".DIR.1");
794 return 1;
795 }
796 #endif /* VMS */
797 /* Process as Unix format: just remove any final slash.
798 But leave "/" unchanged; do not change it to "". */
799 strcpy (dst, src);
800 #ifdef APOLLO
801 /* Handle // as root for apollo's. */
802 if ((slen > 2 && dst[slen - 1] == '/')
803 || (slen > 1 && dst[0] != '/' && dst[slen - 1] == '/'))
804 dst[slen - 1] = 0;
805 #else
806 if (slen > 1
807 && IS_DIRECTORY_SEP (dst[slen - 1])
808 #ifdef DOS_NT
809 && !IS_ANY_SEP (dst[slen - 2])
810 #endif
811 )
812 dst[slen - 1] = 0;
813 #endif
814 #ifdef DOS_NT
815 CORRECT_DIR_SEPS (dst);
816 #endif
817 return 1;
818 }
819
820 DEFUN ("directory-file-name", Fdirectory_file_name, Sdirectory_file_name,
821 1, 1, 0,
822 doc: /* Returns the file name of the directory named DIRECTORY.
823 This is the name of the file that holds the data for the directory DIRECTORY.
824 This operation exists because a directory is also a file, but its name as
825 a directory is different from its name as a file.
826 In Unix-syntax, this function just removes the final slash.
827 On VMS, given a VMS-syntax directory name such as \"[X.Y]\",
828 it returns a file name such as \"[X]Y.DIR.1\". */)
829 (directory)
830 Lisp_Object directory;
831 {
832 char *buf;
833 Lisp_Object handler;
834
835 CHECK_STRING (directory);
836
837 if (NILP (directory))
838 return Qnil;
839
840 /* If the file name has special constructs in it,
841 call the corresponding file handler. */
842 handler = Ffind_file_name_handler (directory, Qdirectory_file_name);
843 if (!NILP (handler))
844 return call2 (handler, Qdirectory_file_name, directory);
845
846 #ifdef VMS
847 /* 20 extra chars is insufficient for VMS, since we might perform a
848 logical name translation. an equivalence string can be up to 255
849 chars long, so grab that much extra space... - sss */
850 buf = (char *) alloca (SBYTES (directory) + 20 + 255);
851 #else
852 buf = (char *) alloca (SBYTES (directory) + 20);
853 #endif
854 directory_file_name (SDATA (directory), buf);
855 return make_specified_string (buf, -1, strlen (buf),
856 STRING_MULTIBYTE (directory));
857 }
858
859 static char make_temp_name_tbl[64] =
860 {
861 'A','B','C','D','E','F','G','H',
862 'I','J','K','L','M','N','O','P',
863 'Q','R','S','T','U','V','W','X',
864 'Y','Z','a','b','c','d','e','f',
865 'g','h','i','j','k','l','m','n',
866 'o','p','q','r','s','t','u','v',
867 'w','x','y','z','0','1','2','3',
868 '4','5','6','7','8','9','-','_'
869 };
870
871 static unsigned make_temp_name_count, make_temp_name_count_initialized_p;
872
873 /* Value is a temporary file name starting with PREFIX, a string.
874
875 The Emacs process number forms part of the result, so there is
876 no danger of generating a name being used by another process.
877 In addition, this function makes an attempt to choose a name
878 which has no existing file. To make this work, PREFIX should be
879 an absolute file name.
880
881 BASE64_P non-zero means add the pid as 3 characters in base64
882 encoding. In this case, 6 characters will be added to PREFIX to
883 form the file name. Otherwise, if Emacs is running on a system
884 with long file names, add the pid as a decimal number.
885
886 This function signals an error if no unique file name could be
887 generated. */
888
889 Lisp_Object
890 make_temp_name (prefix, base64_p)
891 Lisp_Object prefix;
892 int base64_p;
893 {
894 Lisp_Object val;
895 int len, clen;
896 int pid;
897 unsigned char *p, *data;
898 char pidbuf[20];
899 int pidlen;
900
901 CHECK_STRING (prefix);
902
903 /* VAL is created by adding 6 characters to PREFIX. The first
904 three are the PID of this process, in base 64, and the second
905 three are incremented if the file already exists. This ensures
906 262144 unique file names per PID per PREFIX. */
907
908 pid = (int) getpid ();
909
910 if (base64_p)
911 {
912 pidbuf[0] = make_temp_name_tbl[pid & 63], pid >>= 6;
913 pidbuf[1] = make_temp_name_tbl[pid & 63], pid >>= 6;
914 pidbuf[2] = make_temp_name_tbl[pid & 63], pid >>= 6;
915 pidlen = 3;
916 }
917 else
918 {
919 #ifdef HAVE_LONG_FILE_NAMES
920 sprintf (pidbuf, "%d", pid);
921 pidlen = strlen (pidbuf);
922 #else
923 pidbuf[0] = make_temp_name_tbl[pid & 63], pid >>= 6;
924 pidbuf[1] = make_temp_name_tbl[pid & 63], pid >>= 6;
925 pidbuf[2] = make_temp_name_tbl[pid & 63], pid >>= 6;
926 pidlen = 3;
927 #endif
928 }
929
930 len = SBYTES (prefix); clen = SCHARS (prefix);
931 val = make_uninit_multibyte_string (clen + 3 + pidlen, len + 3 + pidlen);
932 if (!STRING_MULTIBYTE (prefix))
933 STRING_SET_UNIBYTE (val);
934 data = SDATA (val);
935 bcopy(SDATA (prefix), data, len);
936 p = data + len;
937
938 bcopy (pidbuf, p, pidlen);
939 p += pidlen;
940
941 /* Here we try to minimize useless stat'ing when this function is
942 invoked many times successively with the same PREFIX. We achieve
943 this by initializing count to a random value, and incrementing it
944 afterwards.
945
946 We don't want make-temp-name to be called while dumping,
947 because then make_temp_name_count_initialized_p would get set
948 and then make_temp_name_count would not be set when Emacs starts. */
949
950 if (!make_temp_name_count_initialized_p)
951 {
952 make_temp_name_count = (unsigned) time (NULL);
953 make_temp_name_count_initialized_p = 1;
954 }
955
956 while (1)
957 {
958 struct stat ignored;
959 unsigned num = make_temp_name_count;
960
961 p[0] = make_temp_name_tbl[num & 63], num >>= 6;
962 p[1] = make_temp_name_tbl[num & 63], num >>= 6;
963 p[2] = make_temp_name_tbl[num & 63], num >>= 6;
964
965 /* Poor man's congruential RN generator. Replace with
966 ++make_temp_name_count for debugging. */
967 make_temp_name_count += 25229;
968 make_temp_name_count %= 225307;
969
970 if (stat (data, &ignored) < 0)
971 {
972 /* We want to return only if errno is ENOENT. */
973 if (errno == ENOENT)
974 return val;
975 else
976 /* The error here is dubious, but there is little else we
977 can do. The alternatives are to return nil, which is
978 as bad as (and in many cases worse than) throwing the
979 error, or to ignore the error, which will likely result
980 in looping through 225307 stat's, which is not only
981 dog-slow, but also useless since it will fallback to
982 the errow below, anyway. */
983 report_file_error ("Cannot create temporary name for prefix",
984 Fcons (prefix, Qnil));
985 /* not reached */
986 }
987 }
988
989 error ("Cannot create temporary name for prefix `%s'",
990 SDATA (prefix));
991 return Qnil;
992 }
993
994
995 DEFUN ("make-temp-name", Fmake_temp_name, Smake_temp_name, 1, 1, 0,
996 doc: /* Generate temporary file name (string) starting with PREFIX (a string).
997 The Emacs process number forms part of the result,
998 so there is no danger of generating a name being used by another process.
999
1000 In addition, this function makes an attempt to choose a name
1001 which has no existing file. To make this work,
1002 PREFIX should be an absolute file name.
1003
1004 There is a race condition between calling `make-temp-name' and creating the
1005 file which opens all kinds of security holes. For that reason, you should
1006 probably use `make-temp-file' instead, except in three circumstances:
1007
1008 * If you are creating the file in the user's home directory.
1009 * If you are creating a directory rather than an ordinary file.
1010 * If you are taking special precautions as `make-temp-file' does. */)
1011 (prefix)
1012 Lisp_Object prefix;
1013 {
1014 return make_temp_name (prefix, 0);
1015 }
1016
1017
1018 \f
1019 DEFUN ("expand-file-name", Fexpand_file_name, Sexpand_file_name, 1, 2, 0,
1020 doc: /* Convert filename NAME to absolute, and canonicalize it.
1021 Second arg DEFAULT-DIRECTORY is directory to start with if NAME is relative
1022 \(does not start with slash); if DEFAULT-DIRECTORY is nil or missing,
1023 the current buffer's value of default-directory is used.
1024 File name components that are `.' are removed, and
1025 so are file name components followed by `..', along with the `..' itself;
1026 note that these simplifications are done without checking the resulting
1027 file names in the file system.
1028 An initial `~/' expands to your home directory.
1029 An initial `~USER/' expands to USER's home directory.
1030 See also the function `substitute-in-file-name'. */)
1031 (name, default_directory)
1032 Lisp_Object name, default_directory;
1033 {
1034 unsigned char *nm;
1035
1036 register unsigned char *newdir, *p, *o;
1037 int tlen;
1038 unsigned char *target;
1039 struct passwd *pw;
1040 #ifdef VMS
1041 unsigned char * colon = 0;
1042 unsigned char * close = 0;
1043 unsigned char * slash = 0;
1044 unsigned char * brack = 0;
1045 int lbrack = 0, rbrack = 0;
1046 int dots = 0;
1047 #endif /* VMS */
1048 #ifdef DOS_NT
1049 int drive = 0;
1050 int collapse_newdir = 1;
1051 int is_escaped = 0;
1052 #endif /* DOS_NT */
1053 int length;
1054 Lisp_Object handler, result;
1055
1056 CHECK_STRING (name);
1057
1058 /* If the file name has special constructs in it,
1059 call the corresponding file handler. */
1060 handler = Ffind_file_name_handler (name, Qexpand_file_name);
1061 if (!NILP (handler))
1062 return call3 (handler, Qexpand_file_name, name, default_directory);
1063
1064 /* Use the buffer's default-directory if DEFAULT_DIRECTORY is omitted. */
1065 if (NILP (default_directory))
1066 default_directory = current_buffer->directory;
1067 if (! STRINGP (default_directory))
1068 {
1069 #ifdef DOS_NT
1070 /* "/" is not considered a root directory on DOS_NT, so using "/"
1071 here causes an infinite recursion in, e.g., the following:
1072
1073 (let (default-directory)
1074 (expand-file-name "a"))
1075
1076 To avoid this, we set default_directory to the root of the
1077 current drive. */
1078 extern char *emacs_root_dir (void);
1079
1080 default_directory = build_string (emacs_root_dir ());
1081 #else
1082 default_directory = build_string ("/");
1083 #endif
1084 }
1085
1086 if (!NILP (default_directory))
1087 {
1088 handler = Ffind_file_name_handler (default_directory, Qexpand_file_name);
1089 if (!NILP (handler))
1090 return call3 (handler, Qexpand_file_name, name, default_directory);
1091 }
1092
1093 o = SDATA (default_directory);
1094
1095 /* Make sure DEFAULT_DIRECTORY is properly expanded.
1096 It would be better to do this down below where we actually use
1097 default_directory. Unfortunately, calling Fexpand_file_name recursively
1098 could invoke GC, and the strings might be relocated. This would
1099 be annoying because we have pointers into strings lying around
1100 that would need adjusting, and people would add new pointers to
1101 the code and forget to adjust them, resulting in intermittent bugs.
1102 Putting this call here avoids all that crud.
1103
1104 The EQ test avoids infinite recursion. */
1105 if (! NILP (default_directory) && !EQ (default_directory, name)
1106 /* Save time in some common cases - as long as default_directory
1107 is not relative, it can be canonicalized with name below (if it
1108 is needed at all) without requiring it to be expanded now. */
1109 #ifdef DOS_NT
1110 /* Detect MSDOS file names with drive specifiers. */
1111 && ! (IS_DRIVE (o[0]) && IS_DEVICE_SEP (o[1]) && IS_DIRECTORY_SEP (o[2]))
1112 #ifdef WINDOWSNT
1113 /* Detect Windows file names in UNC format. */
1114 && ! (IS_DIRECTORY_SEP (o[0]) && IS_DIRECTORY_SEP (o[1]))
1115 #endif
1116 #else /* not DOS_NT */
1117 /* Detect Unix absolute file names (/... alone is not absolute on
1118 DOS or Windows). */
1119 && ! (IS_DIRECTORY_SEP (o[0]))
1120 #endif /* not DOS_NT */
1121 )
1122 {
1123 struct gcpro gcpro1;
1124
1125 GCPRO1 (name);
1126 default_directory = Fexpand_file_name (default_directory, Qnil);
1127 UNGCPRO;
1128 }
1129
1130 name = FILE_SYSTEM_CASE (name);
1131 nm = SDATA (name);
1132
1133 #ifdef DOS_NT
1134 /* We will force directory separators to be either all \ or /, so make
1135 a local copy to modify, even if there ends up being no change. */
1136 nm = strcpy (alloca (strlen (nm) + 1), nm);
1137
1138 /* Note if special escape prefix is present, but remove for now. */
1139 if (nm[0] == '/' && nm[1] == ':')
1140 {
1141 is_escaped = 1;
1142 nm += 2;
1143 }
1144
1145 /* Find and remove drive specifier if present; this makes nm absolute
1146 even if the rest of the name appears to be relative. Only look for
1147 drive specifier at the beginning. */
1148 if (IS_DRIVE (nm[0]) && IS_DEVICE_SEP (nm[1]))
1149 {
1150 drive = nm[0];
1151 nm += 2;
1152 }
1153
1154 #ifdef WINDOWSNT
1155 /* If we see "c://somedir", we want to strip the first slash after the
1156 colon when stripping the drive letter. Otherwise, this expands to
1157 "//somedir". */
1158 if (drive && IS_DIRECTORY_SEP (nm[0]) && IS_DIRECTORY_SEP (nm[1]))
1159 nm++;
1160 #endif /* WINDOWSNT */
1161 #endif /* DOS_NT */
1162
1163 #ifdef WINDOWSNT
1164 /* Discard any previous drive specifier if nm is now in UNC format. */
1165 if (IS_DIRECTORY_SEP (nm[0]) && IS_DIRECTORY_SEP (nm[1]))
1166 {
1167 drive = 0;
1168 }
1169 #endif
1170
1171 /* If nm is absolute, look for `/./' or `/../' or `//''sequences; if
1172 none are found, we can probably return right away. We will avoid
1173 allocating a new string if name is already fully expanded. */
1174 if (
1175 IS_DIRECTORY_SEP (nm[0])
1176 #ifdef MSDOS
1177 && drive && !is_escaped
1178 #endif
1179 #ifdef WINDOWSNT
1180 && (drive || IS_DIRECTORY_SEP (nm[1])) && !is_escaped
1181 #endif
1182 #ifdef VMS
1183 || index (nm, ':')
1184 #endif /* VMS */
1185 )
1186 {
1187 /* If it turns out that the filename we want to return is just a
1188 suffix of FILENAME, we don't need to go through and edit
1189 things; we just need to construct a new string using data
1190 starting at the middle of FILENAME. If we set lose to a
1191 non-zero value, that means we've discovered that we can't do
1192 that cool trick. */
1193 int lose = 0;
1194
1195 p = nm;
1196 while (*p)
1197 {
1198 /* Since we know the name is absolute, we can assume that each
1199 element starts with a "/". */
1200
1201 /* "." and ".." are hairy. */
1202 if (IS_DIRECTORY_SEP (p[0])
1203 && p[1] == '.'
1204 && (IS_DIRECTORY_SEP (p[2])
1205 || p[2] == 0
1206 || (p[2] == '.' && (IS_DIRECTORY_SEP (p[3])
1207 || p[3] == 0))))
1208 lose = 1;
1209 /* We want to replace multiple `/' in a row with a single
1210 slash. */
1211 else if (p > nm
1212 && IS_DIRECTORY_SEP (p[0])
1213 && IS_DIRECTORY_SEP (p[1]))
1214 lose = 1;
1215
1216 #ifdef VMS
1217 if (p[0] == '\\')
1218 lose = 1;
1219 if (p[0] == '/') {
1220 /* if dev:[dir]/, move nm to / */
1221 if (!slash && p > nm && (brack || colon)) {
1222 nm = (brack ? brack + 1 : colon + 1);
1223 lbrack = rbrack = 0;
1224 brack = 0;
1225 colon = 0;
1226 }
1227 slash = p;
1228 }
1229 if (p[0] == '-')
1230 #ifdef NO_HYPHENS_IN_FILENAMES
1231 if (lbrack == rbrack)
1232 {
1233 /* Avoid clobbering negative version numbers. */
1234 if (dots < 2)
1235 p[0] = '_';
1236 }
1237 else
1238 #endif /* NO_HYPHENS_IN_FILENAMES */
1239 if (lbrack > rbrack &&
1240 ((p[-1] == '.' || p[-1] == '[' || p[-1] == '<') &&
1241 (p[1] == '.' || p[1] == ']' || p[1] == '>')))
1242 lose = 1;
1243 #ifdef NO_HYPHENS_IN_FILENAMES
1244 else
1245 p[0] = '_';
1246 #endif /* NO_HYPHENS_IN_FILENAMES */
1247 /* count open brackets, reset close bracket pointer */
1248 if (p[0] == '[' || p[0] == '<')
1249 lbrack++, brack = 0;
1250 /* count close brackets, set close bracket pointer */
1251 if (p[0] == ']' || p[0] == '>')
1252 rbrack++, brack = p;
1253 /* detect ][ or >< */
1254 if ((p[0] == ']' || p[0] == '>') && (p[1] == '[' || p[1] == '<'))
1255 lose = 1;
1256 if ((p[0] == ':' || p[0] == ']' || p[0] == '>') && p[1] == '~')
1257 nm = p + 1, lose = 1;
1258 if (p[0] == ':' && (colon || slash))
1259 /* if dev1:[dir]dev2:, move nm to dev2: */
1260 if (brack)
1261 {
1262 nm = brack + 1;
1263 brack = 0;
1264 }
1265 /* if /name/dev:, move nm to dev: */
1266 else if (slash)
1267 nm = slash + 1;
1268 /* if node::dev:, move colon following dev */
1269 else if (colon && colon[-1] == ':')
1270 colon = p;
1271 /* if dev1:dev2:, move nm to dev2: */
1272 else if (colon && colon[-1] != ':')
1273 {
1274 nm = colon + 1;
1275 colon = 0;
1276 }
1277 if (p[0] == ':' && !colon)
1278 {
1279 if (p[1] == ':')
1280 p++;
1281 colon = p;
1282 }
1283 if (lbrack == rbrack)
1284 if (p[0] == ';')
1285 dots = 2;
1286 else if (p[0] == '.')
1287 dots++;
1288 #endif /* VMS */
1289 p++;
1290 }
1291 if (!lose)
1292 {
1293 #ifdef VMS
1294 if (index (nm, '/'))
1295 {
1296 nm = sys_translate_unix (nm);
1297 return make_specified_string (nm, -1, strlen (nm),
1298 STRING_MULTIBYTE (name));
1299 }
1300 #endif /* VMS */
1301 #ifdef DOS_NT
1302 /* Make sure directories are all separated with / or \ as
1303 desired, but avoid allocation of a new string when not
1304 required. */
1305 CORRECT_DIR_SEPS (nm);
1306 #ifdef WINDOWSNT
1307 if (IS_DIRECTORY_SEP (nm[1]))
1308 {
1309 if (strcmp (nm, SDATA (name)) != 0)
1310 name = make_specified_string (nm, -1, strlen (nm),
1311 STRING_MULTIBYTE (name));
1312 }
1313 else
1314 #endif
1315 /* drive must be set, so this is okay */
1316 if (strcmp (nm - 2, SDATA (name)) != 0)
1317 {
1318 char temp[] = " :";
1319
1320 name = make_specified_string (nm, -1, p - nm,
1321 STRING_MULTIBYTE (name));
1322 temp[0] = DRIVE_LETTER (drive);
1323 name = concat2 (build_string (temp), name);
1324 }
1325 return name;
1326 #else /* not DOS_NT */
1327 if (nm == SDATA (name))
1328 return name;
1329 return make_specified_string (nm, -1, strlen (nm),
1330 STRING_MULTIBYTE (name));
1331 #endif /* not DOS_NT */
1332 }
1333 }
1334
1335 /* At this point, nm might or might not be an absolute file name. We
1336 need to expand ~ or ~user if present, otherwise prefix nm with
1337 default_directory if nm is not absolute, and finally collapse /./
1338 and /foo/../ sequences.
1339
1340 We set newdir to be the appropriate prefix if one is needed:
1341 - the relevant user directory if nm starts with ~ or ~user
1342 - the specified drive's working dir (DOS/NT only) if nm does not
1343 start with /
1344 - the value of default_directory.
1345
1346 Note that these prefixes are not guaranteed to be absolute (except
1347 for the working dir of a drive). Therefore, to ensure we always
1348 return an absolute name, if the final prefix is not absolute we
1349 append it to the current working directory. */
1350
1351 newdir = 0;
1352
1353 if (nm[0] == '~') /* prefix ~ */
1354 {
1355 if (IS_DIRECTORY_SEP (nm[1])
1356 #ifdef VMS
1357 || nm[1] == ':'
1358 #endif /* VMS */
1359 || nm[1] == 0) /* ~ by itself */
1360 {
1361 if (!(newdir = (unsigned char *) egetenv ("HOME")))
1362 newdir = (unsigned char *) "";
1363 nm++;
1364 #ifdef DOS_NT
1365 collapse_newdir = 0;
1366 #endif
1367 #ifdef VMS
1368 nm++; /* Don't leave the slash in nm. */
1369 #endif /* VMS */
1370 }
1371 else /* ~user/filename */
1372 {
1373 for (p = nm; *p && (!IS_DIRECTORY_SEP (*p)
1374 #ifdef VMS
1375 && *p != ':'
1376 #endif /* VMS */
1377 ); p++);
1378 o = (unsigned char *) alloca (p - nm + 1);
1379 bcopy ((char *) nm, o, p - nm);
1380 o [p - nm] = 0;
1381
1382 pw = (struct passwd *) getpwnam (o + 1);
1383 if (pw)
1384 {
1385 newdir = (unsigned char *) pw -> pw_dir;
1386 #ifdef VMS
1387 nm = p + 1; /* skip the terminator */
1388 #else
1389 nm = p;
1390 #ifdef DOS_NT
1391 collapse_newdir = 0;
1392 #endif
1393 #endif /* VMS */
1394 }
1395
1396 /* If we don't find a user of that name, leave the name
1397 unchanged; don't move nm forward to p. */
1398 }
1399 }
1400
1401 #ifdef DOS_NT
1402 /* On DOS and Windows, nm is absolute if a drive name was specified;
1403 use the drive's current directory as the prefix if needed. */
1404 if (!newdir && drive)
1405 {
1406 /* Get default directory if needed to make nm absolute. */
1407 if (!IS_DIRECTORY_SEP (nm[0]))
1408 {
1409 newdir = alloca (MAXPATHLEN + 1);
1410 if (!getdefdir (toupper (drive) - 'A' + 1, newdir))
1411 newdir = NULL;
1412 }
1413 if (!newdir)
1414 {
1415 /* Either nm starts with /, or drive isn't mounted. */
1416 newdir = alloca (4);
1417 newdir[0] = DRIVE_LETTER (drive);
1418 newdir[1] = ':';
1419 newdir[2] = '/';
1420 newdir[3] = 0;
1421 }
1422 }
1423 #endif /* DOS_NT */
1424
1425 /* Finally, if no prefix has been specified and nm is not absolute,
1426 then it must be expanded relative to default_directory. */
1427
1428 if (1
1429 #ifndef DOS_NT
1430 /* /... alone is not absolute on DOS and Windows. */
1431 && !IS_DIRECTORY_SEP (nm[0])
1432 #endif
1433 #ifdef WINDOWSNT
1434 && !(IS_DIRECTORY_SEP (nm[0]) && IS_DIRECTORY_SEP (nm[1]))
1435 #endif
1436 #ifdef VMS
1437 && !index (nm, ':')
1438 #endif
1439 && !newdir)
1440 {
1441 newdir = SDATA (default_directory);
1442 #ifdef DOS_NT
1443 /* Note if special escape prefix is present, but remove for now. */
1444 if (newdir[0] == '/' && newdir[1] == ':')
1445 {
1446 is_escaped = 1;
1447 newdir += 2;
1448 }
1449 #endif
1450 }
1451
1452 #ifdef DOS_NT
1453 if (newdir)
1454 {
1455 /* First ensure newdir is an absolute name. */
1456 if (
1457 /* Detect MSDOS file names with drive specifiers. */
1458 ! (IS_DRIVE (newdir[0])
1459 && IS_DEVICE_SEP (newdir[1]) && IS_DIRECTORY_SEP (newdir[2]))
1460 #ifdef WINDOWSNT
1461 /* Detect Windows file names in UNC format. */
1462 && ! (IS_DIRECTORY_SEP (newdir[0]) && IS_DIRECTORY_SEP (newdir[1]))
1463 #endif
1464 )
1465 {
1466 /* Effectively, let newdir be (expand-file-name newdir cwd).
1467 Because of the admonition against calling expand-file-name
1468 when we have pointers into lisp strings, we accomplish this
1469 indirectly by prepending newdir to nm if necessary, and using
1470 cwd (or the wd of newdir's drive) as the new newdir. */
1471
1472 if (IS_DRIVE (newdir[0]) && IS_DEVICE_SEP (newdir[1]))
1473 {
1474 drive = newdir[0];
1475 newdir += 2;
1476 }
1477 if (!IS_DIRECTORY_SEP (nm[0]))
1478 {
1479 char * tmp = alloca (strlen (newdir) + strlen (nm) + 2);
1480 file_name_as_directory (tmp, newdir);
1481 strcat (tmp, nm);
1482 nm = tmp;
1483 }
1484 newdir = alloca (MAXPATHLEN + 1);
1485 if (drive)
1486 {
1487 if (!getdefdir (toupper (drive) - 'A' + 1, newdir))
1488 newdir = "/";
1489 }
1490 else
1491 getwd (newdir);
1492 }
1493
1494 /* Strip off drive name from prefix, if present. */
1495 if (IS_DRIVE (newdir[0]) && IS_DEVICE_SEP (newdir[1]))
1496 {
1497 drive = newdir[0];
1498 newdir += 2;
1499 }
1500
1501 /* Keep only a prefix from newdir if nm starts with slash
1502 (//server/share for UNC, nothing otherwise). */
1503 if (IS_DIRECTORY_SEP (nm[0]) && collapse_newdir)
1504 {
1505 #ifdef WINDOWSNT
1506 if (IS_DIRECTORY_SEP (newdir[0]) && IS_DIRECTORY_SEP (newdir[1]))
1507 {
1508 newdir = strcpy (alloca (strlen (newdir) + 1), newdir);
1509 p = newdir + 2;
1510 while (*p && !IS_DIRECTORY_SEP (*p)) p++;
1511 p++;
1512 while (*p && !IS_DIRECTORY_SEP (*p)) p++;
1513 *p = 0;
1514 }
1515 else
1516 #endif
1517 newdir = "";
1518 }
1519 }
1520 #endif /* DOS_NT */
1521
1522 if (newdir)
1523 {
1524 /* Get rid of any slash at the end of newdir, unless newdir is
1525 just / or // (an incomplete UNC name). */
1526 length = strlen (newdir);
1527 if (length > 1 && IS_DIRECTORY_SEP (newdir[length - 1])
1528 #ifdef WINDOWSNT
1529 && !(length == 2 && IS_DIRECTORY_SEP (newdir[0]))
1530 #endif
1531 )
1532 {
1533 unsigned char *temp = (unsigned char *) alloca (length);
1534 bcopy (newdir, temp, length - 1);
1535 temp[length - 1] = 0;
1536 newdir = temp;
1537 }
1538 tlen = length + 1;
1539 }
1540 else
1541 tlen = 0;
1542
1543 /* Now concatenate the directory and name to new space in the stack frame */
1544 tlen += strlen (nm) + 1;
1545 #ifdef DOS_NT
1546 /* Reserve space for drive specifier and escape prefix, since either
1547 or both may need to be inserted. (The Microsoft x86 compiler
1548 produces incorrect code if the following two lines are combined.) */
1549 target = (unsigned char *) alloca (tlen + 4);
1550 target += 4;
1551 #else /* not DOS_NT */
1552 target = (unsigned char *) alloca (tlen);
1553 #endif /* not DOS_NT */
1554 *target = 0;
1555
1556 if (newdir)
1557 {
1558 #ifndef VMS
1559 if (nm[0] == 0 || IS_DIRECTORY_SEP (nm[0]))
1560 {
1561 #ifdef DOS_NT
1562 /* If newdir is effectively "C:/", then the drive letter will have
1563 been stripped and newdir will be "/". Concatenating with an
1564 absolute directory in nm produces "//", which will then be
1565 incorrectly treated as a network share. Ignore newdir in
1566 this case (keeping the drive letter). */
1567 if (!(drive && nm[0] && IS_DIRECTORY_SEP (newdir[0])
1568 && newdir[1] == '\0'))
1569 #endif
1570 strcpy (target, newdir);
1571 }
1572 else
1573 #endif
1574 file_name_as_directory (target, newdir);
1575 }
1576
1577 strcat (target, nm);
1578 #ifdef VMS
1579 if (index (target, '/'))
1580 strcpy (target, sys_translate_unix (target));
1581 #endif /* VMS */
1582
1583 /* ASSERT (IS_DIRECTORY_SEP (target[0])) if not VMS */
1584
1585 /* Now canonicalize by removing `//', `/.' and `/foo/..' if they
1586 appear. */
1587
1588 p = target;
1589 o = target;
1590
1591 while (*p)
1592 {
1593 #ifdef VMS
1594 if (*p != ']' && *p != '>' && *p != '-')
1595 {
1596 if (*p == '\\')
1597 p++;
1598 *o++ = *p++;
1599 }
1600 else if ((p[0] == ']' || p[0] == '>') && p[0] == p[1] + 2)
1601 /* brackets are offset from each other by 2 */
1602 {
1603 p += 2;
1604 if (*p != '.' && *p != '-' && o[-1] != '.')
1605 /* convert [foo][bar] to [bar] */
1606 while (o[-1] != '[' && o[-1] != '<')
1607 o--;
1608 else if (*p == '-' && *o != '.')
1609 *--p = '.';
1610 }
1611 else if (p[0] == '-' && o[-1] == '.' &&
1612 (p[1] == '.' || p[1] == ']' || p[1] == '>'))
1613 /* flush .foo.- ; leave - if stopped by '[' or '<' */
1614 {
1615 do
1616 o--;
1617 while (o[-1] != '.' && o[-1] != '[' && o[-1] != '<');
1618 if (p[1] == '.') /* foo.-.bar ==> bar. */
1619 p += 2;
1620 else if (o[-1] == '.') /* '.foo.-]' ==> ']' */
1621 p++, o--;
1622 /* else [foo.-] ==> [-] */
1623 }
1624 else
1625 {
1626 #ifdef NO_HYPHENS_IN_FILENAMES
1627 if (*p == '-' &&
1628 o[-1] != '[' && o[-1] != '<' && o[-1] != '.' &&
1629 p[1] != ']' && p[1] != '>' && p[1] != '.')
1630 *p = '_';
1631 #endif /* NO_HYPHENS_IN_FILENAMES */
1632 *o++ = *p++;
1633 }
1634 #else /* not VMS */
1635 if (!IS_DIRECTORY_SEP (*p))
1636 {
1637 *o++ = *p++;
1638 }
1639 else if (IS_DIRECTORY_SEP (p[0])
1640 && p[1] == '.'
1641 && (IS_DIRECTORY_SEP (p[2])
1642 || p[2] == 0))
1643 {
1644 /* If "/." is the entire filename, keep the "/". Otherwise,
1645 just delete the whole "/.". */
1646 if (o == target && p[2] == '\0')
1647 *o++ = *p;
1648 p += 2;
1649 }
1650 else if (IS_DIRECTORY_SEP (p[0]) && p[1] == '.' && p[2] == '.'
1651 /* `/../' is the "superroot" on certain file systems. */
1652 && o != target
1653 && (IS_DIRECTORY_SEP (p[3]) || p[3] == 0))
1654 {
1655 while (o != target && (--o) && !IS_DIRECTORY_SEP (*o))
1656 ;
1657 /* Keep initial / only if this is the whole name. */
1658 if (o == target && IS_ANY_SEP (*o) && p[3] == 0)
1659 ++o;
1660 p += 3;
1661 }
1662 else if (p > target
1663 && IS_DIRECTORY_SEP (p[0]) && IS_DIRECTORY_SEP (p[1]))
1664 {
1665 /* Collapse multiple `/' in a row. */
1666 *o++ = *p++;
1667 while (IS_DIRECTORY_SEP (*p))
1668 ++p;
1669 }
1670 else
1671 {
1672 *o++ = *p++;
1673 }
1674 #endif /* not VMS */
1675 }
1676
1677 #ifdef DOS_NT
1678 /* At last, set drive name. */
1679 #ifdef WINDOWSNT
1680 /* Except for network file name. */
1681 if (!(IS_DIRECTORY_SEP (target[0]) && IS_DIRECTORY_SEP (target[1])))
1682 #endif /* WINDOWSNT */
1683 {
1684 if (!drive) abort ();
1685 target -= 2;
1686 target[0] = DRIVE_LETTER (drive);
1687 target[1] = ':';
1688 }
1689 /* Reinsert the escape prefix if required. */
1690 if (is_escaped)
1691 {
1692 target -= 2;
1693 target[0] = '/';
1694 target[1] = ':';
1695 }
1696 CORRECT_DIR_SEPS (target);
1697 #endif /* DOS_NT */
1698
1699 result = make_specified_string (target, -1, o - target,
1700 STRING_MULTIBYTE (name));
1701
1702 /* Again look to see if the file name has special constructs in it
1703 and perhaps call the corresponding file handler. This is needed
1704 for filenames such as "/foo/../user@host:/bar/../baz". Expanding
1705 the ".." component gives us "/user@host:/bar/../baz" which needs
1706 to be expanded again. */
1707 handler = Ffind_file_name_handler (result, Qexpand_file_name);
1708 if (!NILP (handler))
1709 return call3 (handler, Qexpand_file_name, result, default_directory);
1710
1711 return result;
1712 }
1713
1714 #if 0
1715 /* PLEASE DO NOT DELETE THIS COMMENTED-OUT VERSION!
1716 This is the old version of expand-file-name, before it was thoroughly
1717 rewritten for Emacs 10.31. We leave this version here commented-out,
1718 because the code is very complex and likely to have subtle bugs. If
1719 bugs _are_ found, it might be of interest to look at the old code and
1720 see what did it do in the relevant situation.
1721
1722 Don't remove this code: it's true that it will be accessible via CVS,
1723 but a few years from deletion, people will forget it is there. */
1724
1725 /* Changed this DEFUN to a DEAFUN, so as not to confuse `make-docfile'. */
1726 DEAFUN ("expand-file-name", Fexpand_file_name, Sexpand_file_name, 1, 2, 0,
1727 "Convert FILENAME to absolute, and canonicalize it.\n\
1728 Second arg DEFAULT is directory to start with if FILENAME is relative\n\
1729 \(does not start with slash); if DEFAULT is nil or missing,\n\
1730 the current buffer's value of default-directory is used.\n\
1731 Filenames containing `.' or `..' as components are simplified;\n\
1732 initial `~/' expands to your home directory.\n\
1733 See also the function `substitute-in-file-name'.")
1734 (name, defalt)
1735 Lisp_Object name, defalt;
1736 {
1737 unsigned char *nm;
1738
1739 register unsigned char *newdir, *p, *o;
1740 int tlen;
1741 unsigned char *target;
1742 struct passwd *pw;
1743 int lose;
1744 #ifdef VMS
1745 unsigned char * colon = 0;
1746 unsigned char * close = 0;
1747 unsigned char * slash = 0;
1748 unsigned char * brack = 0;
1749 int lbrack = 0, rbrack = 0;
1750 int dots = 0;
1751 #endif /* VMS */
1752
1753 CHECK_STRING (name);
1754
1755 #ifdef VMS
1756 /* Filenames on VMS are always upper case. */
1757 name = Fupcase (name);
1758 #endif
1759
1760 nm = SDATA (name);
1761
1762 /* If nm is absolute, flush ...// and detect /./ and /../.
1763 If no /./ or /../ we can return right away. */
1764 if (
1765 nm[0] == '/'
1766 #ifdef VMS
1767 || index (nm, ':')
1768 #endif /* VMS */
1769 )
1770 {
1771 p = nm;
1772 lose = 0;
1773 while (*p)
1774 {
1775 if (p[0] == '/' && p[1] == '/'
1776 #ifdef APOLLO
1777 /* // at start of filename is meaningful on Apollo system. */
1778 && nm != p
1779 #endif /* APOLLO */
1780 )
1781 nm = p + 1;
1782 if (p[0] == '/' && p[1] == '~')
1783 nm = p + 1, lose = 1;
1784 if (p[0] == '/' && p[1] == '.'
1785 && (p[2] == '/' || p[2] == 0
1786 || (p[2] == '.' && (p[3] == '/' || p[3] == 0))))
1787 lose = 1;
1788 #ifdef VMS
1789 if (p[0] == '\\')
1790 lose = 1;
1791 if (p[0] == '/') {
1792 /* if dev:[dir]/, move nm to / */
1793 if (!slash && p > nm && (brack || colon)) {
1794 nm = (brack ? brack + 1 : colon + 1);
1795 lbrack = rbrack = 0;
1796 brack = 0;
1797 colon = 0;
1798 }
1799 slash = p;
1800 }
1801 if (p[0] == '-')
1802 #ifndef VMS4_4
1803 /* VMS pre V4.4,convert '-'s in filenames. */
1804 if (lbrack == rbrack)
1805 {
1806 if (dots < 2) /* this is to allow negative version numbers */
1807 p[0] = '_';
1808 }
1809 else
1810 #endif /* VMS4_4 */
1811 if (lbrack > rbrack &&
1812 ((p[-1] == '.' || p[-1] == '[' || p[-1] == '<') &&
1813 (p[1] == '.' || p[1] == ']' || p[1] == '>')))
1814 lose = 1;
1815 #ifndef VMS4_4
1816 else
1817 p[0] = '_';
1818 #endif /* VMS4_4 */
1819 /* count open brackets, reset close bracket pointer */
1820 if (p[0] == '[' || p[0] == '<')
1821 lbrack++, brack = 0;
1822 /* count close brackets, set close bracket pointer */
1823 if (p[0] == ']' || p[0] == '>')
1824 rbrack++, brack = p;
1825 /* detect ][ or >< */
1826 if ((p[0] == ']' || p[0] == '>') && (p[1] == '[' || p[1] == '<'))
1827 lose = 1;
1828 if ((p[0] == ':' || p[0] == ']' || p[0] == '>') && p[1] == '~')
1829 nm = p + 1, lose = 1;
1830 if (p[0] == ':' && (colon || slash))
1831 /* if dev1:[dir]dev2:, move nm to dev2: */
1832 if (brack)
1833 {
1834 nm = brack + 1;
1835 brack = 0;
1836 }
1837 /* If /name/dev:, move nm to dev: */
1838 else if (slash)
1839 nm = slash + 1;
1840 /* If node::dev:, move colon following dev */
1841 else if (colon && colon[-1] == ':')
1842 colon = p;
1843 /* If dev1:dev2:, move nm to dev2: */
1844 else if (colon && colon[-1] != ':')
1845 {
1846 nm = colon + 1;
1847 colon = 0;
1848 }
1849 if (p[0] == ':' && !colon)
1850 {
1851 if (p[1] == ':')
1852 p++;
1853 colon = p;
1854 }
1855 if (lbrack == rbrack)
1856 if (p[0] == ';')
1857 dots = 2;
1858 else if (p[0] == '.')
1859 dots++;
1860 #endif /* VMS */
1861 p++;
1862 }
1863 if (!lose)
1864 {
1865 #ifdef VMS
1866 if (index (nm, '/'))
1867 return build_string (sys_translate_unix (nm));
1868 #endif /* VMS */
1869 if (nm == SDATA (name))
1870 return name;
1871 return build_string (nm);
1872 }
1873 }
1874
1875 /* Now determine directory to start with and put it in NEWDIR */
1876
1877 newdir = 0;
1878
1879 if (nm[0] == '~') /* prefix ~ */
1880 if (nm[1] == '/'
1881 #ifdef VMS
1882 || nm[1] == ':'
1883 #endif /* VMS */
1884 || nm[1] == 0)/* ~/filename */
1885 {
1886 if (!(newdir = (unsigned char *) egetenv ("HOME")))
1887 newdir = (unsigned char *) "";
1888 nm++;
1889 #ifdef VMS
1890 nm++; /* Don't leave the slash in nm. */
1891 #endif /* VMS */
1892 }
1893 else /* ~user/filename */
1894 {
1895 /* Get past ~ to user */
1896 unsigned char *user = nm + 1;
1897 /* Find end of name. */
1898 unsigned char *ptr = (unsigned char *) index (user, '/');
1899 int len = ptr ? ptr - user : strlen (user);
1900 #ifdef VMS
1901 unsigned char *ptr1 = index (user, ':');
1902 if (ptr1 != 0 && ptr1 - user < len)
1903 len = ptr1 - user;
1904 #endif /* VMS */
1905 /* Copy the user name into temp storage. */
1906 o = (unsigned char *) alloca (len + 1);
1907 bcopy ((char *) user, o, len);
1908 o[len] = 0;
1909
1910 /* Look up the user name. */
1911 pw = (struct passwd *) getpwnam (o + 1);
1912 if (!pw)
1913 error ("\"%s\" isn't a registered user", o + 1);
1914
1915 newdir = (unsigned char *) pw->pw_dir;
1916
1917 /* Discard the user name from NM. */
1918 nm += len;
1919 }
1920
1921 if (nm[0] != '/'
1922 #ifdef VMS
1923 && !index (nm, ':')
1924 #endif /* not VMS */
1925 && !newdir)
1926 {
1927 if (NILP (defalt))
1928 defalt = current_buffer->directory;
1929 CHECK_STRING (defalt);
1930 newdir = SDATA (defalt);
1931 }
1932
1933 /* Now concatenate the directory and name to new space in the stack frame */
1934
1935 tlen = (newdir ? strlen (newdir) + 1 : 0) + strlen (nm) + 1;
1936 target = (unsigned char *) alloca (tlen);
1937 *target = 0;
1938
1939 if (newdir)
1940 {
1941 #ifndef VMS
1942 if (nm[0] == 0 || nm[0] == '/')
1943 strcpy (target, newdir);
1944 else
1945 #endif
1946 file_name_as_directory (target, newdir);
1947 }
1948
1949 strcat (target, nm);
1950 #ifdef VMS
1951 if (index (target, '/'))
1952 strcpy (target, sys_translate_unix (target));
1953 #endif /* VMS */
1954
1955 /* Now canonicalize by removing /. and /foo/.. if they appear */
1956
1957 p = target;
1958 o = target;
1959
1960 while (*p)
1961 {
1962 #ifdef VMS
1963 if (*p != ']' && *p != '>' && *p != '-')
1964 {
1965 if (*p == '\\')
1966 p++;
1967 *o++ = *p++;
1968 }
1969 else if ((p[0] == ']' || p[0] == '>') && p[0] == p[1] + 2)
1970 /* brackets are offset from each other by 2 */
1971 {
1972 p += 2;
1973 if (*p != '.' && *p != '-' && o[-1] != '.')
1974 /* convert [foo][bar] to [bar] */
1975 while (o[-1] != '[' && o[-1] != '<')
1976 o--;
1977 else if (*p == '-' && *o != '.')
1978 *--p = '.';
1979 }
1980 else if (p[0] == '-' && o[-1] == '.' &&
1981 (p[1] == '.' || p[1] == ']' || p[1] == '>'))
1982 /* flush .foo.- ; leave - if stopped by '[' or '<' */
1983 {
1984 do
1985 o--;
1986 while (o[-1] != '.' && o[-1] != '[' && o[-1] != '<');
1987 if (p[1] == '.') /* foo.-.bar ==> bar. */
1988 p += 2;
1989 else if (o[-1] == '.') /* '.foo.-]' ==> ']' */
1990 p++, o--;
1991 /* else [foo.-] ==> [-] */
1992 }
1993 else
1994 {
1995 #ifndef VMS4_4
1996 if (*p == '-' &&
1997 o[-1] != '[' && o[-1] != '<' && o[-1] != '.' &&
1998 p[1] != ']' && p[1] != '>' && p[1] != '.')
1999 *p = '_';
2000 #endif /* VMS4_4 */
2001 *o++ = *p++;
2002 }
2003 #else /* not VMS */
2004 if (*p != '/')
2005 {
2006 *o++ = *p++;
2007 }
2008 else if (!strncmp (p, "//", 2)
2009 #ifdef APOLLO
2010 /* // at start of filename is meaningful in Apollo system. */
2011 && o != target
2012 #endif /* APOLLO */
2013 )
2014 {
2015 o = target;
2016 p++;
2017 }
2018 else if (p[0] == '/' && p[1] == '.' &&
2019 (p[2] == '/' || p[2] == 0))
2020 p += 2;
2021 else if (!strncmp (p, "/..", 3)
2022 /* `/../' is the "superroot" on certain file systems. */
2023 && o != target
2024 && (p[3] == '/' || p[3] == 0))
2025 {
2026 while (o != target && *--o != '/')
2027 ;
2028 #ifdef APOLLO
2029 if (o == target + 1 && o[-1] == '/' && o[0] == '/')
2030 ++o;
2031 else
2032 #endif /* APOLLO */
2033 if (o == target && *o == '/')
2034 ++o;
2035 p += 3;
2036 }
2037 else
2038 {
2039 *o++ = *p++;
2040 }
2041 #endif /* not VMS */
2042 }
2043
2044 return make_string (target, o - target);
2045 }
2046 #endif
2047 \f
2048 /* If /~ or // appears, discard everything through first slash. */
2049 static int
2050 file_name_absolute_p (filename)
2051 const unsigned char *filename;
2052 {
2053 return
2054 (IS_DIRECTORY_SEP (*filename) || *filename == '~'
2055 #ifdef VMS
2056 /* ??? This criterion is probably wrong for '<'. */
2057 || index (filename, ':') || index (filename, '<')
2058 || (*filename == '[' && (filename[1] != '-'
2059 || (filename[2] != '.' && filename[2] != ']'))
2060 && filename[1] != '.')
2061 #endif /* VMS */
2062 #ifdef DOS_NT
2063 || (IS_DRIVE (*filename) && IS_DEVICE_SEP (filename[1])
2064 && IS_DIRECTORY_SEP (filename[2]))
2065 #endif
2066 );
2067 }
2068
2069 static unsigned char *
2070 search_embedded_absfilename (nm, endp)
2071 unsigned char *nm, *endp;
2072 {
2073 unsigned char *p, *s;
2074
2075 for (p = nm + 1; p < endp; p++)
2076 {
2077 if ((0
2078 #ifdef VMS
2079 || p[-1] == ':' || p[-1] == ']' || p[-1] == '>'
2080 #endif /* VMS */
2081 || IS_DIRECTORY_SEP (p[-1]))
2082 && file_name_absolute_p (p)
2083 #if defined (APOLLO) || defined (WINDOWSNT) || defined(CYGWIN)
2084 /* // at start of file name is meaningful in Apollo,
2085 WindowsNT and Cygwin systems. */
2086 && !(IS_DIRECTORY_SEP (p[0]) && p - 1 == nm)
2087 #endif /* not (APOLLO || WINDOWSNT || CYGWIN) */
2088 )
2089 {
2090 for (s = p; *s && (!IS_DIRECTORY_SEP (*s)
2091 #ifdef VMS
2092 && *s != ':'
2093 #endif /* VMS */
2094 ); s++);
2095 if (p[0] == '~' && s > p + 1) /* we've got "/~something/" */
2096 {
2097 unsigned char *o = alloca (s - p + 1);
2098 struct passwd *pw;
2099 bcopy (p, o, s - p);
2100 o [s - p] = 0;
2101
2102 /* If we have ~user and `user' exists, discard
2103 everything up to ~. But if `user' does not exist, leave
2104 ~user alone, it might be a literal file name. */
2105 if ((pw = getpwnam (o + 1)))
2106 return p;
2107 else
2108 xfree (pw);
2109 }
2110 else
2111 return p;
2112 }
2113 }
2114 return NULL;
2115 }
2116
2117 DEFUN ("substitute-in-file-name", Fsubstitute_in_file_name,
2118 Ssubstitute_in_file_name, 1, 1, 0,
2119 doc: /* Substitute environment variables referred to in FILENAME.
2120 `$FOO' where FOO is an environment variable name means to substitute
2121 the value of that variable. The variable name should be terminated
2122 with a character not a letter, digit or underscore; otherwise, enclose
2123 the entire variable name in braces.
2124 If `/~' appears, all of FILENAME through that `/' is discarded.
2125
2126 On VMS, `$' substitution is not done; this function does little and only
2127 duplicates what `expand-file-name' does. */)
2128 (filename)
2129 Lisp_Object filename;
2130 {
2131 unsigned char *nm;
2132
2133 register unsigned char *s, *p, *o, *x, *endp;
2134 unsigned char *target = NULL;
2135 int total = 0;
2136 int substituted = 0;
2137 unsigned char *xnm;
2138 Lisp_Object handler;
2139
2140 CHECK_STRING (filename);
2141
2142 /* If the file name has special constructs in it,
2143 call the corresponding file handler. */
2144 handler = Ffind_file_name_handler (filename, Qsubstitute_in_file_name);
2145 if (!NILP (handler))
2146 return call2 (handler, Qsubstitute_in_file_name, filename);
2147
2148 nm = SDATA (filename);
2149 #ifdef DOS_NT
2150 nm = strcpy (alloca (strlen (nm) + 1), nm);
2151 CORRECT_DIR_SEPS (nm);
2152 substituted = (strcmp (nm, SDATA (filename)) != 0);
2153 #endif
2154 endp = nm + SBYTES (filename);
2155
2156 /* If /~ or // appears, discard everything through first slash. */
2157 p = search_embedded_absfilename (nm, endp);
2158 if (p)
2159 /* Start over with the new string, so we check the file-name-handler
2160 again. Important with filenames like "/home/foo//:/hello///there"
2161 which whould substitute to "/:/hello///there" rather than "/there". */
2162 return Fsubstitute_in_file_name
2163 (make_specified_string (p, -1, endp - p,
2164 STRING_MULTIBYTE (filename)));
2165
2166 #ifdef VMS
2167 return filename;
2168 #else
2169
2170 /* See if any variables are substituted into the string
2171 and find the total length of their values in `total' */
2172
2173 for (p = nm; p != endp;)
2174 if (*p != '$')
2175 p++;
2176 else
2177 {
2178 p++;
2179 if (p == endp)
2180 goto badsubst;
2181 else if (*p == '$')
2182 {
2183 /* "$$" means a single "$" */
2184 p++;
2185 total -= 1;
2186 substituted = 1;
2187 continue;
2188 }
2189 else if (*p == '{')
2190 {
2191 o = ++p;
2192 while (p != endp && *p != '}') p++;
2193 if (*p != '}') goto missingclose;
2194 s = p;
2195 }
2196 else
2197 {
2198 o = p;
2199 while (p != endp && (isalnum (*p) || *p == '_')) p++;
2200 s = p;
2201 }
2202
2203 /* Copy out the variable name */
2204 target = (unsigned char *) alloca (s - o + 1);
2205 strncpy (target, o, s - o);
2206 target[s - o] = 0;
2207 #ifdef DOS_NT
2208 strupr (target); /* $home == $HOME etc. */
2209 #endif /* DOS_NT */
2210
2211 /* Get variable value */
2212 o = (unsigned char *) egetenv (target);
2213 if (o)
2214 {
2215 total += strlen (o);
2216 substituted = 1;
2217 }
2218 else if (*p == '}')
2219 goto badvar;
2220 }
2221
2222 if (!substituted)
2223 return filename;
2224
2225 /* If substitution required, recopy the string and do it */
2226 /* Make space in stack frame for the new copy */
2227 xnm = (unsigned char *) alloca (SBYTES (filename) + total + 1);
2228 x = xnm;
2229
2230 /* Copy the rest of the name through, replacing $ constructs with values */
2231 for (p = nm; *p;)
2232 if (*p != '$')
2233 *x++ = *p++;
2234 else
2235 {
2236 p++;
2237 if (p == endp)
2238 goto badsubst;
2239 else if (*p == '$')
2240 {
2241 *x++ = *p++;
2242 continue;
2243 }
2244 else if (*p == '{')
2245 {
2246 o = ++p;
2247 while (p != endp && *p != '}') p++;
2248 if (*p != '}') goto missingclose;
2249 s = p++;
2250 }
2251 else
2252 {
2253 o = p;
2254 while (p != endp && (isalnum (*p) || *p == '_')) p++;
2255 s = p;
2256 }
2257
2258 /* Copy out the variable name */
2259 target = (unsigned char *) alloca (s - o + 1);
2260 strncpy (target, o, s - o);
2261 target[s - o] = 0;
2262 #ifdef DOS_NT
2263 strupr (target); /* $home == $HOME etc. */
2264 #endif /* DOS_NT */
2265
2266 /* Get variable value */
2267 o = (unsigned char *) egetenv (target);
2268 if (!o)
2269 {
2270 *x++ = '$';
2271 strcpy (x, target); x+= strlen (target);
2272 }
2273 else if (STRING_MULTIBYTE (filename))
2274 {
2275 /* If the original string is multibyte,
2276 convert what we substitute into multibyte. */
2277 while (*o)
2278 {
2279 int c = unibyte_char_to_multibyte (*o++);
2280 x += CHAR_STRING (c, x);
2281 }
2282 }
2283 else
2284 {
2285 strcpy (x, o);
2286 x += strlen (o);
2287 }
2288 }
2289
2290 *x = 0;
2291
2292 /* If /~ or // appears, discard everything through first slash. */
2293 while ((p = search_embedded_absfilename (xnm, x)))
2294 /* This time we do not start over because we've already expanded envvars
2295 and replaced $$ with $. Maybe we should start over as well, but we'd
2296 need to quote some $ to $$ first. */
2297 xnm = p;
2298
2299 return make_specified_string (xnm, -1, x - xnm, STRING_MULTIBYTE (filename));
2300
2301 badsubst:
2302 error ("Bad format environment-variable substitution");
2303 missingclose:
2304 error ("Missing \"}\" in environment-variable substitution");
2305 badvar:
2306 error ("Substituting nonexistent environment variable \"%s\"", target);
2307
2308 /* NOTREACHED */
2309 #endif /* not VMS */
2310 return Qnil;
2311 }
2312 \f
2313 /* A slightly faster and more convenient way to get
2314 (directory-file-name (expand-file-name FOO)). */
2315
2316 Lisp_Object
2317 expand_and_dir_to_file (filename, defdir)
2318 Lisp_Object filename, defdir;
2319 {
2320 register Lisp_Object absname;
2321
2322 absname = Fexpand_file_name (filename, defdir);
2323 #ifdef VMS
2324 {
2325 register int c = SREF (absname, SBYTES (absname) - 1);
2326 if (c == ':' || c == ']' || c == '>')
2327 absname = Fdirectory_file_name (absname);
2328 }
2329 #else
2330 /* Remove final slash, if any (unless this is the root dir).
2331 stat behaves differently depending! */
2332 if (SCHARS (absname) > 1
2333 && IS_DIRECTORY_SEP (SREF (absname, SBYTES (absname) - 1))
2334 && !IS_DEVICE_SEP (SREF (absname, SBYTES (absname)-2)))
2335 /* We cannot take shortcuts; they might be wrong for magic file names. */
2336 absname = Fdirectory_file_name (absname);
2337 #endif
2338 return absname;
2339 }
2340 \f
2341 /* Signal an error if the file ABSNAME already exists.
2342 If INTERACTIVE is nonzero, ask the user whether to proceed,
2343 and bypass the error if the user says to go ahead.
2344 QUERYSTRING is a name for the action that is being considered
2345 to alter the file.
2346
2347 *STATPTR is used to store the stat information if the file exists.
2348 If the file does not exist, STATPTR->st_mode is set to 0.
2349 If STATPTR is null, we don't store into it.
2350
2351 If QUICK is nonzero, we ask for y or n, not yes or no. */
2352
2353 void
2354 barf_or_query_if_file_exists (absname, querystring, interactive, statptr, quick)
2355 Lisp_Object absname;
2356 unsigned char *querystring;
2357 int interactive;
2358 struct stat *statptr;
2359 int quick;
2360 {
2361 register Lisp_Object tem, encoded_filename;
2362 struct stat statbuf;
2363 struct gcpro gcpro1;
2364
2365 encoded_filename = ENCODE_FILE (absname);
2366
2367 /* stat is a good way to tell whether the file exists,
2368 regardless of what access permissions it has. */
2369 if (lstat (SDATA (encoded_filename), &statbuf) >= 0)
2370 {
2371 if (! interactive)
2372 Fsignal (Qfile_already_exists,
2373 Fcons (build_string ("File already exists"),
2374 Fcons (absname, Qnil)));
2375 GCPRO1 (absname);
2376 tem = format2 ("File %s already exists; %s anyway? ",
2377 absname, build_string (querystring));
2378 if (quick)
2379 tem = Fy_or_n_p (tem);
2380 else
2381 tem = do_yes_or_no_p (tem);
2382 UNGCPRO;
2383 if (NILP (tem))
2384 Fsignal (Qfile_already_exists,
2385 Fcons (build_string ("File already exists"),
2386 Fcons (absname, Qnil)));
2387 if (statptr)
2388 *statptr = statbuf;
2389 }
2390 else
2391 {
2392 if (statptr)
2393 statptr->st_mode = 0;
2394 }
2395 return;
2396 }
2397
2398 DEFUN ("copy-file", Fcopy_file, Scopy_file, 2, 5,
2399 "fCopy file: \nGCopy %s to file: \np\nP",
2400 doc: /* Copy FILE to NEWNAME. Both args must be strings.
2401 If NEWNAME names a directory, copy FILE there.
2402 Signals a `file-already-exists' error if file NEWNAME already exists,
2403 unless a third argument OK-IF-ALREADY-EXISTS is supplied and non-nil.
2404 A number as third arg means request confirmation if NEWNAME already exists.
2405 This is what happens in interactive use with M-x.
2406 Always sets the file modes of the output file to match the input file.
2407
2408 Fourth arg KEEP-TIME non-nil means give the output file the same
2409 last-modified time as the old one. (This works on only some systems.)
2410
2411 A prefix arg makes KEEP-TIME non-nil.
2412
2413 The optional fifth arg MUSTBENEW, if non-nil, insists on a check
2414 for an existing file with the same name. If MUSTBENEW is `excl',
2415 that means to get an error if the file already exists; never overwrite.
2416 If MUSTBENEW is neither nil nor `excl', that means ask for
2417 confirmation before overwriting, but do go ahead and overwrite the file
2418 if the user confirms. */)
2419 (file, newname, ok_if_already_exists, keep_time, mustbenew)
2420 Lisp_Object file, newname, ok_if_already_exists, keep_time, mustbenew;
2421 {
2422 int ifd, ofd, n;
2423 char buf[16 * 1024];
2424 struct stat st, out_st;
2425 Lisp_Object handler;
2426 struct gcpro gcpro1, gcpro2, gcpro3, gcpro4;
2427 int count = SPECPDL_INDEX ();
2428 int input_file_statable_p;
2429 Lisp_Object encoded_file, encoded_newname;
2430
2431 encoded_file = encoded_newname = Qnil;
2432 GCPRO4 (file, newname, encoded_file, encoded_newname);
2433 CHECK_STRING (file);
2434 CHECK_STRING (newname);
2435
2436 if (!NILP (mustbenew) && !EQ (mustbenew, Qexcl))
2437 barf_or_query_if_file_exists (newname, "overwrite", 1, 0, 1);
2438
2439 if (!NILP (Ffile_directory_p (newname)))
2440 newname = Fexpand_file_name (Ffile_name_nondirectory (file), newname);
2441 else
2442 newname = Fexpand_file_name (newname, Qnil);
2443
2444 file = Fexpand_file_name (file, Qnil);
2445
2446 /* If the input file name has special constructs in it,
2447 call the corresponding file handler. */
2448 handler = Ffind_file_name_handler (file, Qcopy_file);
2449 /* Likewise for output file name. */
2450 if (NILP (handler))
2451 handler = Ffind_file_name_handler (newname, Qcopy_file);
2452 if (!NILP (handler))
2453 RETURN_UNGCPRO (call5 (handler, Qcopy_file, file, newname,
2454 ok_if_already_exists, keep_time));
2455
2456 encoded_file = ENCODE_FILE (file);
2457 encoded_newname = ENCODE_FILE (newname);
2458
2459 if (NILP (ok_if_already_exists)
2460 || INTEGERP (ok_if_already_exists))
2461 barf_or_query_if_file_exists (encoded_newname, "copy to it",
2462 INTEGERP (ok_if_already_exists), &out_st, 0);
2463 else if (stat (SDATA (encoded_newname), &out_st) < 0)
2464 out_st.st_mode = 0;
2465
2466 #ifdef WINDOWSNT
2467 if (!CopyFile (SDATA (encoded_file),
2468 SDATA (encoded_newname),
2469 FALSE))
2470 report_file_error ("Copying file", Fcons (file, Fcons (newname, Qnil)));
2471 /* CopyFile retains the timestamp by default. */
2472 else if (NILP (keep_time))
2473 {
2474 EMACS_TIME now;
2475 DWORD attributes;
2476 char * filename;
2477
2478 EMACS_GET_TIME (now);
2479 filename = SDATA (encoded_newname);
2480
2481 /* Ensure file is writable while its modified time is set. */
2482 attributes = GetFileAttributes (filename);
2483 SetFileAttributes (filename, attributes & ~FILE_ATTRIBUTE_READONLY);
2484 if (set_file_times (filename, now, now))
2485 {
2486 /* Restore original attributes. */
2487 SetFileAttributes (filename, attributes);
2488 Fsignal (Qfile_date_error,
2489 Fcons (build_string ("Cannot set file date"),
2490 Fcons (newname, Qnil)));
2491 }
2492 /* Restore original attributes. */
2493 SetFileAttributes (filename, attributes);
2494 }
2495 #else /* not WINDOWSNT */
2496 immediate_quit = 1;
2497 ifd = emacs_open (SDATA (encoded_file), O_RDONLY, 0);
2498 immediate_quit = 0;
2499
2500 if (ifd < 0)
2501 report_file_error ("Opening input file", Fcons (file, Qnil));
2502
2503 record_unwind_protect (close_file_unwind, make_number (ifd));
2504
2505 /* We can only copy regular files and symbolic links. Other files are not
2506 copyable by us. */
2507 input_file_statable_p = (fstat (ifd, &st) >= 0);
2508
2509 #if !defined (DOS_NT) || __DJGPP__ > 1
2510 if (out_st.st_mode != 0
2511 && st.st_dev == out_st.st_dev && st.st_ino == out_st.st_ino)
2512 {
2513 errno = 0;
2514 report_file_error ("Input and output files are the same",
2515 Fcons (file, Fcons (newname, Qnil)));
2516 }
2517 #endif
2518
2519 #if defined (S_ISREG) && defined (S_ISLNK)
2520 if (input_file_statable_p)
2521 {
2522 if (!(S_ISREG (st.st_mode)) && !(S_ISLNK (st.st_mode)))
2523 {
2524 #if defined (EISDIR)
2525 /* Get a better looking error message. */
2526 errno = EISDIR;
2527 #endif /* EISDIR */
2528 report_file_error ("Non-regular file", Fcons (file, Qnil));
2529 }
2530 }
2531 #endif /* S_ISREG && S_ISLNK */
2532
2533 #ifdef VMS
2534 /* Create the copy file with the same record format as the input file */
2535 ofd = sys_creat (SDATA (encoded_newname), 0666, ifd);
2536 #else
2537 #ifdef MSDOS
2538 /* System's default file type was set to binary by _fmode in emacs.c. */
2539 ofd = emacs_open (SDATA (encoded_newname),
2540 O_WRONLY | O_TRUNC | O_CREAT
2541 | (EQ (mustbenew, Qexcl) ? O_EXCL : 0),
2542 S_IREAD | S_IWRITE);
2543 #else /* not MSDOS */
2544 ofd = emacs_open (SDATA (encoded_newname),
2545 O_WRONLY | O_TRUNC | O_CREAT
2546 | (EQ (mustbenew, Qexcl) ? O_EXCL : 0),
2547 0666);
2548 #endif /* not MSDOS */
2549 #endif /* VMS */
2550 if (ofd < 0)
2551 report_file_error ("Opening output file", Fcons (newname, Qnil));
2552
2553 record_unwind_protect (close_file_unwind, make_number (ofd));
2554
2555 immediate_quit = 1;
2556 QUIT;
2557 while ((n = emacs_read (ifd, buf, sizeof buf)) > 0)
2558 if (emacs_write (ofd, buf, n) != n)
2559 report_file_error ("I/O error", Fcons (newname, Qnil));
2560 immediate_quit = 0;
2561
2562 /* Closing the output clobbers the file times on some systems. */
2563 if (emacs_close (ofd) < 0)
2564 report_file_error ("I/O error", Fcons (newname, Qnil));
2565
2566 if (input_file_statable_p)
2567 {
2568 if (!NILP (keep_time))
2569 {
2570 EMACS_TIME atime, mtime;
2571 EMACS_SET_SECS_USECS (atime, st.st_atime, 0);
2572 EMACS_SET_SECS_USECS (mtime, st.st_mtime, 0);
2573 if (set_file_times (SDATA (encoded_newname),
2574 atime, mtime))
2575 Fsignal (Qfile_date_error,
2576 Fcons (build_string ("Cannot set file date"),
2577 Fcons (newname, Qnil)));
2578 }
2579 #ifndef MSDOS
2580 chmod (SDATA (encoded_newname), st.st_mode & 07777);
2581 #else /* MSDOS */
2582 #if defined (__DJGPP__) && __DJGPP__ > 1
2583 /* In DJGPP v2.0 and later, fstat usually returns true file mode bits,
2584 and if it can't, it tells so. Otherwise, under MSDOS we usually
2585 get only the READ bit, which will make the copied file read-only,
2586 so it's better not to chmod at all. */
2587 if ((_djstat_flags & _STFAIL_WRITEBIT) == 0)
2588 chmod (SDATA (encoded_newname), st.st_mode & 07777);
2589 #endif /* DJGPP version 2 or newer */
2590 #endif /* MSDOS */
2591 }
2592
2593 emacs_close (ifd);
2594 #endif /* WINDOWSNT */
2595
2596 /* Discard the unwind protects. */
2597 specpdl_ptr = specpdl + count;
2598
2599 UNGCPRO;
2600 return Qnil;
2601 }
2602 \f
2603 DEFUN ("make-directory-internal", Fmake_directory_internal,
2604 Smake_directory_internal, 1, 1, 0,
2605 doc: /* Create a new directory named DIRECTORY. */)
2606 (directory)
2607 Lisp_Object directory;
2608 {
2609 const unsigned char *dir;
2610 Lisp_Object handler;
2611 Lisp_Object encoded_dir;
2612
2613 CHECK_STRING (directory);
2614 directory = Fexpand_file_name (directory, Qnil);
2615
2616 handler = Ffind_file_name_handler (directory, Qmake_directory_internal);
2617 if (!NILP (handler))
2618 return call2 (handler, Qmake_directory_internal, directory);
2619
2620 encoded_dir = ENCODE_FILE (directory);
2621
2622 dir = SDATA (encoded_dir);
2623
2624 #ifdef WINDOWSNT
2625 if (mkdir (dir) != 0)
2626 #else
2627 if (mkdir (dir, 0777) != 0)
2628 #endif
2629 report_file_error ("Creating directory", Flist (1, &directory));
2630
2631 return Qnil;
2632 }
2633
2634 DEFUN ("delete-directory", Fdelete_directory, Sdelete_directory, 1, 1, "FDelete directory: ",
2635 doc: /* Delete the directory named DIRECTORY. Does not follow symlinks. */)
2636 (directory)
2637 Lisp_Object directory;
2638 {
2639 const unsigned char *dir;
2640 Lisp_Object handler;
2641 Lisp_Object encoded_dir;
2642
2643 CHECK_STRING (directory);
2644 directory = Fdirectory_file_name (Fexpand_file_name (directory, Qnil));
2645
2646 handler = Ffind_file_name_handler (directory, Qdelete_directory);
2647 if (!NILP (handler))
2648 return call2 (handler, Qdelete_directory, directory);
2649
2650 encoded_dir = ENCODE_FILE (directory);
2651
2652 dir = SDATA (encoded_dir);
2653
2654 if (rmdir (dir) != 0)
2655 report_file_error ("Removing directory", Flist (1, &directory));
2656
2657 return Qnil;
2658 }
2659
2660 DEFUN ("delete-file", Fdelete_file, Sdelete_file, 1, 1, "fDelete file: ",
2661 doc: /* Delete file named FILENAME. If it is a symlink, remove the symlink.
2662 If file has multiple names, it continues to exist with the other names. */)
2663 (filename)
2664 Lisp_Object filename;
2665 {
2666 Lisp_Object handler;
2667 Lisp_Object encoded_file;
2668 struct gcpro gcpro1;
2669
2670 GCPRO1 (filename);
2671 if (!NILP (Ffile_directory_p (filename))
2672 && NILP (Ffile_symlink_p (filename)))
2673 Fsignal (Qfile_error,
2674 Fcons (build_string ("Removing old name: is a directory"),
2675 Fcons (filename, Qnil)));
2676 UNGCPRO;
2677 filename = Fexpand_file_name (filename, Qnil);
2678
2679 handler = Ffind_file_name_handler (filename, Qdelete_file);
2680 if (!NILP (handler))
2681 return call2 (handler, Qdelete_file, filename);
2682
2683 encoded_file = ENCODE_FILE (filename);
2684
2685 if (0 > unlink (SDATA (encoded_file)))
2686 report_file_error ("Removing old name", Flist (1, &filename));
2687 return Qnil;
2688 }
2689
2690 static Lisp_Object
2691 internal_delete_file_1 (ignore)
2692 Lisp_Object ignore;
2693 {
2694 return Qt;
2695 }
2696
2697 /* Delete file FILENAME, returning 1 if successful and 0 if failed. */
2698
2699 int
2700 internal_delete_file (filename)
2701 Lisp_Object filename;
2702 {
2703 return NILP (internal_condition_case_1 (Fdelete_file, filename,
2704 Qt, internal_delete_file_1));
2705 }
2706 \f
2707 DEFUN ("rename-file", Frename_file, Srename_file, 2, 3,
2708 "fRename file: \nGRename %s to file: \np",
2709 doc: /* Rename FILE as NEWNAME. Both args strings.
2710 If file has names other than FILE, it continues to have those names.
2711 Signals a `file-already-exists' error if a file NEWNAME already exists
2712 unless optional third argument OK-IF-ALREADY-EXISTS is non-nil.
2713 A number as third arg means request confirmation if NEWNAME already exists.
2714 This is what happens in interactive use with M-x. */)
2715 (file, newname, ok_if_already_exists)
2716 Lisp_Object file, newname, ok_if_already_exists;
2717 {
2718 #ifdef NO_ARG_ARRAY
2719 Lisp_Object args[2];
2720 #endif
2721 Lisp_Object handler;
2722 struct gcpro gcpro1, gcpro2, gcpro3, gcpro4, gcpro5;
2723 Lisp_Object encoded_file, encoded_newname, symlink_target;
2724
2725 symlink_target = encoded_file = encoded_newname = Qnil;
2726 GCPRO5 (file, newname, encoded_file, encoded_newname, symlink_target);
2727 CHECK_STRING (file);
2728 CHECK_STRING (newname);
2729 file = Fexpand_file_name (file, Qnil);
2730
2731 if (!NILP (Ffile_directory_p (newname)))
2732 newname = Fexpand_file_name (Ffile_name_nondirectory (file), newname);
2733 else
2734 newname = Fexpand_file_name (newname, Qnil);
2735
2736 /* If the file name has special constructs in it,
2737 call the corresponding file handler. */
2738 handler = Ffind_file_name_handler (file, Qrename_file);
2739 if (NILP (handler))
2740 handler = Ffind_file_name_handler (newname, Qrename_file);
2741 if (!NILP (handler))
2742 RETURN_UNGCPRO (call4 (handler, Qrename_file,
2743 file, newname, ok_if_already_exists));
2744
2745 encoded_file = ENCODE_FILE (file);
2746 encoded_newname = ENCODE_FILE (newname);
2747
2748 #ifdef DOS_NT
2749 /* If the file names are identical but for the case, don't ask for
2750 confirmation: they simply want to change the letter-case of the
2751 file name. */
2752 if (NILP (Fstring_equal (Fdowncase (file), Fdowncase (newname))))
2753 #endif
2754 if (NILP (ok_if_already_exists)
2755 || INTEGERP (ok_if_already_exists))
2756 barf_or_query_if_file_exists (encoded_newname, "rename to it",
2757 INTEGERP (ok_if_already_exists), 0, 0);
2758 #ifndef BSD4_1
2759 if (0 > rename (SDATA (encoded_file), SDATA (encoded_newname)))
2760 #else
2761 if (0 > link (SDATA (encoded_file), SDATA (encoded_newname))
2762 || 0 > unlink (SDATA (encoded_file)))
2763 #endif
2764 {
2765 if (errno == EXDEV)
2766 {
2767 #ifdef S_IFLNK
2768 symlink_target = Ffile_symlink_p (file);
2769 if (! NILP (symlink_target))
2770 Fmake_symbolic_link (symlink_target, newname,
2771 NILP (ok_if_already_exists) ? Qnil : Qt);
2772 else
2773 #endif
2774 Fcopy_file (file, newname,
2775 /* We have already prompted if it was an integer,
2776 so don't have copy-file prompt again. */
2777 NILP (ok_if_already_exists) ? Qnil : Qt,
2778 Qt, Qnil);
2779 Fdelete_file (file);
2780 }
2781 else
2782 #ifdef NO_ARG_ARRAY
2783 {
2784 args[0] = file;
2785 args[1] = newname;
2786 report_file_error ("Renaming", Flist (2, args));
2787 }
2788 #else
2789 report_file_error ("Renaming", Flist (2, &file));
2790 #endif
2791 }
2792 UNGCPRO;
2793 return Qnil;
2794 }
2795
2796 DEFUN ("add-name-to-file", Fadd_name_to_file, Sadd_name_to_file, 2, 3,
2797 "fAdd name to file: \nGName to add to %s: \np",
2798 doc: /* Give FILE additional name NEWNAME. Both args strings.
2799 Signals a `file-already-exists' error if a file NEWNAME already exists
2800 unless optional third argument OK-IF-ALREADY-EXISTS is non-nil.
2801 A number as third arg means request confirmation if NEWNAME already exists.
2802 This is what happens in interactive use with M-x. */)
2803 (file, newname, ok_if_already_exists)
2804 Lisp_Object file, newname, ok_if_already_exists;
2805 {
2806 #ifdef NO_ARG_ARRAY
2807 Lisp_Object args[2];
2808 #endif
2809 Lisp_Object handler;
2810 Lisp_Object encoded_file, encoded_newname;
2811 struct gcpro gcpro1, gcpro2, gcpro3, gcpro4;
2812
2813 GCPRO4 (file, newname, encoded_file, encoded_newname);
2814 encoded_file = encoded_newname = Qnil;
2815 CHECK_STRING (file);
2816 CHECK_STRING (newname);
2817 file = Fexpand_file_name (file, Qnil);
2818
2819 if (!NILP (Ffile_directory_p (newname)))
2820 newname = Fexpand_file_name (Ffile_name_nondirectory (file), newname);
2821 else
2822 newname = Fexpand_file_name (newname, Qnil);
2823
2824 /* If the file name has special constructs in it,
2825 call the corresponding file handler. */
2826 handler = Ffind_file_name_handler (file, Qadd_name_to_file);
2827 if (!NILP (handler))
2828 RETURN_UNGCPRO (call4 (handler, Qadd_name_to_file, file,
2829 newname, ok_if_already_exists));
2830
2831 /* If the new name has special constructs in it,
2832 call the corresponding file handler. */
2833 handler = Ffind_file_name_handler (newname, Qadd_name_to_file);
2834 if (!NILP (handler))
2835 RETURN_UNGCPRO (call4 (handler, Qadd_name_to_file, file,
2836 newname, ok_if_already_exists));
2837
2838 encoded_file = ENCODE_FILE (file);
2839 encoded_newname = ENCODE_FILE (newname);
2840
2841 if (NILP (ok_if_already_exists)
2842 || INTEGERP (ok_if_already_exists))
2843 barf_or_query_if_file_exists (encoded_newname, "make it a new name",
2844 INTEGERP (ok_if_already_exists), 0, 0);
2845
2846 unlink (SDATA (newname));
2847 if (0 > link (SDATA (encoded_file), SDATA (encoded_newname)))
2848 {
2849 #ifdef NO_ARG_ARRAY
2850 args[0] = file;
2851 args[1] = newname;
2852 report_file_error ("Adding new name", Flist (2, args));
2853 #else
2854 report_file_error ("Adding new name", Flist (2, &file));
2855 #endif
2856 }
2857
2858 UNGCPRO;
2859 return Qnil;
2860 }
2861
2862 #ifdef S_IFLNK
2863 DEFUN ("make-symbolic-link", Fmake_symbolic_link, Smake_symbolic_link, 2, 3,
2864 "FMake symbolic link to file: \nGMake symbolic link to file %s: \np",
2865 doc: /* Make a symbolic link to FILENAME, named LINKNAME. Both args strings.
2866 Signals a `file-already-exists' error if a file LINKNAME already exists
2867 unless optional third argument OK-IF-ALREADY-EXISTS is non-nil.
2868 A number as third arg means request confirmation if LINKNAME already exists.
2869 This happens for interactive use with M-x. */)
2870 (filename, linkname, ok_if_already_exists)
2871 Lisp_Object filename, linkname, ok_if_already_exists;
2872 {
2873 #ifdef NO_ARG_ARRAY
2874 Lisp_Object args[2];
2875 #endif
2876 Lisp_Object handler;
2877 Lisp_Object encoded_filename, encoded_linkname;
2878 struct gcpro gcpro1, gcpro2, gcpro3, gcpro4;
2879
2880 GCPRO4 (filename, linkname, encoded_filename, encoded_linkname);
2881 encoded_filename = encoded_linkname = Qnil;
2882 CHECK_STRING (filename);
2883 CHECK_STRING (linkname);
2884 /* If the link target has a ~, we must expand it to get
2885 a truly valid file name. Otherwise, do not expand;
2886 we want to permit links to relative file names. */
2887 if (SREF (filename, 0) == '~')
2888 filename = Fexpand_file_name (filename, Qnil);
2889
2890 if (!NILP (Ffile_directory_p (linkname)))
2891 linkname = Fexpand_file_name (Ffile_name_nondirectory (filename), linkname);
2892 else
2893 linkname = Fexpand_file_name (linkname, Qnil);
2894
2895 /* If the file name has special constructs in it,
2896 call the corresponding file handler. */
2897 handler = Ffind_file_name_handler (filename, Qmake_symbolic_link);
2898 if (!NILP (handler))
2899 RETURN_UNGCPRO (call4 (handler, Qmake_symbolic_link, filename,
2900 linkname, ok_if_already_exists));
2901
2902 /* If the new link name has special constructs in it,
2903 call the corresponding file handler. */
2904 handler = Ffind_file_name_handler (linkname, Qmake_symbolic_link);
2905 if (!NILP (handler))
2906 RETURN_UNGCPRO (call4 (handler, Qmake_symbolic_link, filename,
2907 linkname, ok_if_already_exists));
2908
2909 encoded_filename = ENCODE_FILE (filename);
2910 encoded_linkname = ENCODE_FILE (linkname);
2911
2912 if (NILP (ok_if_already_exists)
2913 || INTEGERP (ok_if_already_exists))
2914 barf_or_query_if_file_exists (encoded_linkname, "make it a link",
2915 INTEGERP (ok_if_already_exists), 0, 0);
2916 if (0 > symlink (SDATA (encoded_filename),
2917 SDATA (encoded_linkname)))
2918 {
2919 /* If we didn't complain already, silently delete existing file. */
2920 if (errno == EEXIST)
2921 {
2922 unlink (SDATA (encoded_linkname));
2923 if (0 <= symlink (SDATA (encoded_filename),
2924 SDATA (encoded_linkname)))
2925 {
2926 UNGCPRO;
2927 return Qnil;
2928 }
2929 }
2930
2931 #ifdef NO_ARG_ARRAY
2932 args[0] = filename;
2933 args[1] = linkname;
2934 report_file_error ("Making symbolic link", Flist (2, args));
2935 #else
2936 report_file_error ("Making symbolic link", Flist (2, &filename));
2937 #endif
2938 }
2939 UNGCPRO;
2940 return Qnil;
2941 }
2942 #endif /* S_IFLNK */
2943
2944 #ifdef VMS
2945
2946 DEFUN ("define-logical-name", Fdefine_logical_name, Sdefine_logical_name,
2947 2, 2, "sDefine logical name: \nsDefine logical name %s as: ",
2948 doc: /* Define the job-wide logical name NAME to have the value STRING.
2949 If STRING is nil or a null string, the logical name NAME is deleted. */)
2950 (name, string)
2951 Lisp_Object name;
2952 Lisp_Object string;
2953 {
2954 CHECK_STRING (name);
2955 if (NILP (string))
2956 delete_logical_name (SDATA (name));
2957 else
2958 {
2959 CHECK_STRING (string);
2960
2961 if (SCHARS (string) == 0)
2962 delete_logical_name (SDATA (name));
2963 else
2964 define_logical_name (SDATA (name), SDATA (string));
2965 }
2966
2967 return string;
2968 }
2969 #endif /* VMS */
2970
2971 #ifdef HPUX_NET
2972
2973 DEFUN ("sysnetunam", Fsysnetunam, Ssysnetunam, 2, 2, 0,
2974 doc: /* Open a network connection to PATH using LOGIN as the login string. */)
2975 (path, login)
2976 Lisp_Object path, login;
2977 {
2978 int netresult;
2979
2980 CHECK_STRING (path);
2981 CHECK_STRING (login);
2982
2983 netresult = netunam (SDATA (path), SDATA (login));
2984
2985 if (netresult == -1)
2986 return Qnil;
2987 else
2988 return Qt;
2989 }
2990 #endif /* HPUX_NET */
2991 \f
2992 DEFUN ("file-name-absolute-p", Ffile_name_absolute_p, Sfile_name_absolute_p,
2993 1, 1, 0,
2994 doc: /* Return t if file FILENAME specifies an absolute file name.
2995 On Unix, this is a name starting with a `/' or a `~'. */)
2996 (filename)
2997 Lisp_Object filename;
2998 {
2999 CHECK_STRING (filename);
3000 return file_name_absolute_p (SDATA (filename)) ? Qt : Qnil;
3001 }
3002 \f
3003 /* Return nonzero if file FILENAME exists and can be executed. */
3004
3005 static int
3006 check_executable (filename)
3007 char *filename;
3008 {
3009 #ifdef DOS_NT
3010 int len = strlen (filename);
3011 char *suffix;
3012 struct stat st;
3013 if (stat (filename, &st) < 0)
3014 return 0;
3015 #if defined (WINDOWSNT) || (defined (MSDOS) && __DJGPP__ > 1)
3016 return ((st.st_mode & S_IEXEC) != 0);
3017 #else
3018 return (S_ISREG (st.st_mode)
3019 && len >= 5
3020 && (stricmp ((suffix = filename + len-4), ".com") == 0
3021 || stricmp (suffix, ".exe") == 0
3022 || stricmp (suffix, ".bat") == 0)
3023 || (st.st_mode & S_IFMT) == S_IFDIR);
3024 #endif /* not WINDOWSNT */
3025 #else /* not DOS_NT */
3026 #ifdef HAVE_EUIDACCESS
3027 return (euidaccess (filename, 1) >= 0);
3028 #else
3029 /* Access isn't quite right because it uses the real uid
3030 and we really want to test with the effective uid.
3031 But Unix doesn't give us a right way to do it. */
3032 return (access (filename, 1) >= 0);
3033 #endif
3034 #endif /* not DOS_NT */
3035 }
3036
3037 /* Return nonzero if file FILENAME exists and can be written. */
3038
3039 static int
3040 check_writable (filename)
3041 char *filename;
3042 {
3043 #ifdef MSDOS
3044 struct stat st;
3045 if (stat (filename, &st) < 0)
3046 return 0;
3047 return (st.st_mode & S_IWRITE || (st.st_mode & S_IFMT) == S_IFDIR);
3048 #else /* not MSDOS */
3049 #ifdef HAVE_EUIDACCESS
3050 return (euidaccess (filename, 2) >= 0);
3051 #else
3052 /* Access isn't quite right because it uses the real uid
3053 and we really want to test with the effective uid.
3054 But Unix doesn't give us a right way to do it.
3055 Opening with O_WRONLY could work for an ordinary file,
3056 but would lose for directories. */
3057 return (access (filename, 2) >= 0);
3058 #endif
3059 #endif /* not MSDOS */
3060 }
3061
3062 DEFUN ("file-exists-p", Ffile_exists_p, Sfile_exists_p, 1, 1, 0,
3063 doc: /* Return t if file FILENAME exists. (This does not mean you can read it.)
3064 See also `file-readable-p' and `file-attributes'. */)
3065 (filename)
3066 Lisp_Object filename;
3067 {
3068 Lisp_Object absname;
3069 Lisp_Object handler;
3070 struct stat statbuf;
3071
3072 CHECK_STRING (filename);
3073 absname = Fexpand_file_name (filename, Qnil);
3074
3075 /* If the file name has special constructs in it,
3076 call the corresponding file handler. */
3077 handler = Ffind_file_name_handler (absname, Qfile_exists_p);
3078 if (!NILP (handler))
3079 return call2 (handler, Qfile_exists_p, absname);
3080
3081 absname = ENCODE_FILE (absname);
3082
3083 return (stat (SDATA (absname), &statbuf) >= 0) ? Qt : Qnil;
3084 }
3085
3086 DEFUN ("file-executable-p", Ffile_executable_p, Sfile_executable_p, 1, 1, 0,
3087 doc: /* Return t if FILENAME can be executed by you.
3088 For a directory, this means you can access files in that directory. */)
3089 (filename)
3090 Lisp_Object filename;
3091 {
3092 Lisp_Object absname;
3093 Lisp_Object handler;
3094
3095 CHECK_STRING (filename);
3096 absname = Fexpand_file_name (filename, Qnil);
3097
3098 /* If the file name has special constructs in it,
3099 call the corresponding file handler. */
3100 handler = Ffind_file_name_handler (absname, Qfile_executable_p);
3101 if (!NILP (handler))
3102 return call2 (handler, Qfile_executable_p, absname);
3103
3104 absname = ENCODE_FILE (absname);
3105
3106 return (check_executable (SDATA (absname)) ? Qt : Qnil);
3107 }
3108
3109 DEFUN ("file-readable-p", Ffile_readable_p, Sfile_readable_p, 1, 1, 0,
3110 doc: /* Return t if file FILENAME exists and you can read it.
3111 See also `file-exists-p' and `file-attributes'. */)
3112 (filename)
3113 Lisp_Object filename;
3114 {
3115 Lisp_Object absname;
3116 Lisp_Object handler;
3117 int desc;
3118 int flags;
3119 struct stat statbuf;
3120
3121 CHECK_STRING (filename);
3122 absname = Fexpand_file_name (filename, Qnil);
3123
3124 /* If the file name has special constructs in it,
3125 call the corresponding file handler. */
3126 handler = Ffind_file_name_handler (absname, Qfile_readable_p);
3127 if (!NILP (handler))
3128 return call2 (handler, Qfile_readable_p, absname);
3129
3130 absname = ENCODE_FILE (absname);
3131
3132 #if defined(DOS_NT) || defined(macintosh)
3133 /* Under MS-DOS, Windows, and Macintosh, open does not work for
3134 directories. */
3135 if (access (SDATA (absname), 0) == 0)
3136 return Qt;
3137 return Qnil;
3138 #else /* not DOS_NT and not macintosh */
3139 flags = O_RDONLY;
3140 #if defined (S_ISFIFO) && defined (O_NONBLOCK)
3141 /* Opening a fifo without O_NONBLOCK can wait.
3142 We don't want to wait. But we don't want to mess wth O_NONBLOCK
3143 except in the case of a fifo, on a system which handles it. */
3144 desc = stat (SDATA (absname), &statbuf);
3145 if (desc < 0)
3146 return Qnil;
3147 if (S_ISFIFO (statbuf.st_mode))
3148 flags |= O_NONBLOCK;
3149 #endif
3150 desc = emacs_open (SDATA (absname), flags, 0);
3151 if (desc < 0)
3152 return Qnil;
3153 emacs_close (desc);
3154 return Qt;
3155 #endif /* not DOS_NT and not macintosh */
3156 }
3157
3158 /* Having this before file-symlink-p mysteriously caused it to be forgotten
3159 on the RT/PC. */
3160 DEFUN ("file-writable-p", Ffile_writable_p, Sfile_writable_p, 1, 1, 0,
3161 doc: /* Return t if file FILENAME can be written or created by you. */)
3162 (filename)
3163 Lisp_Object filename;
3164 {
3165 Lisp_Object absname, dir, encoded;
3166 Lisp_Object handler;
3167 struct stat statbuf;
3168
3169 CHECK_STRING (filename);
3170 absname = Fexpand_file_name (filename, Qnil);
3171
3172 /* If the file name has special constructs in it,
3173 call the corresponding file handler. */
3174 handler = Ffind_file_name_handler (absname, Qfile_writable_p);
3175 if (!NILP (handler))
3176 return call2 (handler, Qfile_writable_p, absname);
3177
3178 encoded = ENCODE_FILE (absname);
3179 if (stat (SDATA (encoded), &statbuf) >= 0)
3180 return (check_writable (SDATA (encoded))
3181 ? Qt : Qnil);
3182
3183 dir = Ffile_name_directory (absname);
3184 #ifdef VMS
3185 if (!NILP (dir))
3186 dir = Fdirectory_file_name (dir);
3187 #endif /* VMS */
3188 #ifdef MSDOS
3189 if (!NILP (dir))
3190 dir = Fdirectory_file_name (dir);
3191 #endif /* MSDOS */
3192
3193 dir = ENCODE_FILE (dir);
3194 #ifdef WINDOWSNT
3195 /* The read-only attribute of the parent directory doesn't affect
3196 whether a file or directory can be created within it. Some day we
3197 should check ACLs though, which do affect this. */
3198 if (stat (SDATA (dir), &statbuf) < 0)
3199 return Qnil;
3200 return (statbuf.st_mode & S_IFMT) == S_IFDIR ? Qt : Qnil;
3201 #else
3202 return (check_writable (!NILP (dir) ? (char *) SDATA (dir) : "")
3203 ? Qt : Qnil);
3204 #endif
3205 }
3206 \f
3207 DEFUN ("access-file", Faccess_file, Saccess_file, 2, 2, 0,
3208 doc: /* Access file FILENAME, and get an error if that does not work.
3209 The second argument STRING is used in the error message.
3210 If there is no error, we return nil. */)
3211 (filename, string)
3212 Lisp_Object filename, string;
3213 {
3214 Lisp_Object handler, encoded_filename, absname;
3215 int fd;
3216
3217 CHECK_STRING (filename);
3218 absname = Fexpand_file_name (filename, Qnil);
3219
3220 CHECK_STRING (string);
3221
3222 /* If the file name has special constructs in it,
3223 call the corresponding file handler. */
3224 handler = Ffind_file_name_handler (absname, Qaccess_file);
3225 if (!NILP (handler))
3226 return call3 (handler, Qaccess_file, absname, string);
3227
3228 encoded_filename = ENCODE_FILE (absname);
3229
3230 fd = emacs_open (SDATA (encoded_filename), O_RDONLY, 0);
3231 if (fd < 0)
3232 report_file_error (SDATA (string), Fcons (filename, Qnil));
3233 emacs_close (fd);
3234
3235 return Qnil;
3236 }
3237 \f
3238 DEFUN ("file-symlink-p", Ffile_symlink_p, Sfile_symlink_p, 1, 1, 0,
3239 doc: /* Return non-nil if file FILENAME is the name of a symbolic link.
3240 The value is the link target, as a string.
3241 Otherwise returns nil. */)
3242 (filename)
3243 Lisp_Object filename;
3244 {
3245 Lisp_Object handler;
3246
3247 CHECK_STRING (filename);
3248 filename = Fexpand_file_name (filename, Qnil);
3249
3250 /* If the file name has special constructs in it,
3251 call the corresponding file handler. */
3252 handler = Ffind_file_name_handler (filename, Qfile_symlink_p);
3253 if (!NILP (handler))
3254 return call2 (handler, Qfile_symlink_p, filename);
3255
3256 #ifdef S_IFLNK
3257 {
3258 char *buf;
3259 int bufsize;
3260 int valsize;
3261 Lisp_Object val;
3262
3263 filename = ENCODE_FILE (filename);
3264
3265 bufsize = 50;
3266 buf = NULL;
3267 do
3268 {
3269 bufsize *= 2;
3270 buf = (char *) xrealloc (buf, bufsize);
3271 bzero (buf, bufsize);
3272
3273 errno = 0;
3274 valsize = readlink (SDATA (filename), buf, bufsize);
3275 if (valsize == -1)
3276 {
3277 #ifdef ERANGE
3278 /* HP-UX reports ERANGE if buffer is too small. */
3279 if (errno == ERANGE)
3280 valsize = bufsize;
3281 else
3282 #endif
3283 {
3284 xfree (buf);
3285 return Qnil;
3286 }
3287 }
3288 }
3289 while (valsize >= bufsize);
3290
3291 val = make_string (buf, valsize);
3292 if (buf[0] == '/' && index (buf, ':'))
3293 val = concat2 (build_string ("/:"), val);
3294 xfree (buf);
3295 val = DECODE_FILE (val);
3296 return val;
3297 }
3298 #else /* not S_IFLNK */
3299 return Qnil;
3300 #endif /* not S_IFLNK */
3301 }
3302
3303 DEFUN ("file-directory-p", Ffile_directory_p, Sfile_directory_p, 1, 1, 0,
3304 doc: /* Return t if FILENAME names an existing directory.
3305 Symbolic links to directories count as directories.
3306 See `file-symlink-p' to distinguish symlinks. */)
3307 (filename)
3308 Lisp_Object filename;
3309 {
3310 register Lisp_Object absname;
3311 struct stat st;
3312 Lisp_Object handler;
3313
3314 absname = expand_and_dir_to_file (filename, current_buffer->directory);
3315
3316 /* If the file name has special constructs in it,
3317 call the corresponding file handler. */
3318 handler = Ffind_file_name_handler (absname, Qfile_directory_p);
3319 if (!NILP (handler))
3320 return call2 (handler, Qfile_directory_p, absname);
3321
3322 absname = ENCODE_FILE (absname);
3323
3324 if (stat (SDATA (absname), &st) < 0)
3325 return Qnil;
3326 return (st.st_mode & S_IFMT) == S_IFDIR ? Qt : Qnil;
3327 }
3328
3329 DEFUN ("file-accessible-directory-p", Ffile_accessible_directory_p, Sfile_accessible_directory_p, 1, 1, 0,
3330 doc: /* Return t if file FILENAME names a directory you can open.
3331 For the value to be t, FILENAME must specify the name of a directory as a file,
3332 and the directory must allow you to open files in it. In order to use a
3333 directory as a buffer's current directory, this predicate must return true.
3334 A directory name spec may be given instead; then the value is t
3335 if the directory so specified exists and really is a readable and
3336 searchable directory. */)
3337 (filename)
3338 Lisp_Object filename;
3339 {
3340 Lisp_Object handler;
3341 int tem;
3342 struct gcpro gcpro1;
3343
3344 /* If the file name has special constructs in it,
3345 call the corresponding file handler. */
3346 handler = Ffind_file_name_handler (filename, Qfile_accessible_directory_p);
3347 if (!NILP (handler))
3348 return call2 (handler, Qfile_accessible_directory_p, filename);
3349
3350 GCPRO1 (filename);
3351 tem = (NILP (Ffile_directory_p (filename))
3352 || NILP (Ffile_executable_p (filename)));
3353 UNGCPRO;
3354 return tem ? Qnil : Qt;
3355 }
3356
3357 DEFUN ("file-regular-p", Ffile_regular_p, Sfile_regular_p, 1, 1, 0,
3358 doc: /* Return t if file FILENAME is the name of a regular file.
3359 This is the sort of file that holds an ordinary stream of data bytes. */)
3360 (filename)
3361 Lisp_Object filename;
3362 {
3363 register Lisp_Object absname;
3364 struct stat st;
3365 Lisp_Object handler;
3366
3367 absname = expand_and_dir_to_file (filename, current_buffer->directory);
3368
3369 /* If the file name has special constructs in it,
3370 call the corresponding file handler. */
3371 handler = Ffind_file_name_handler (absname, Qfile_regular_p);
3372 if (!NILP (handler))
3373 return call2 (handler, Qfile_regular_p, absname);
3374
3375 absname = ENCODE_FILE (absname);
3376
3377 #ifdef WINDOWSNT
3378 {
3379 int result;
3380 Lisp_Object tem = Vw32_get_true_file_attributes;
3381
3382 /* Tell stat to use expensive method to get accurate info. */
3383 Vw32_get_true_file_attributes = Qt;
3384 result = stat (SDATA (absname), &st);
3385 Vw32_get_true_file_attributes = tem;
3386
3387 if (result < 0)
3388 return Qnil;
3389 return (st.st_mode & S_IFMT) == S_IFREG ? Qt : Qnil;
3390 }
3391 #else
3392 if (stat (SDATA (absname), &st) < 0)
3393 return Qnil;
3394 return (st.st_mode & S_IFMT) == S_IFREG ? Qt : Qnil;
3395 #endif
3396 }
3397 \f
3398 DEFUN ("file-modes", Ffile_modes, Sfile_modes, 1, 1, 0,
3399 doc: /* Return mode bits of file named FILENAME, as an integer.
3400 Return nil, if file does not exist or is not accessible. */)
3401 (filename)
3402 Lisp_Object filename;
3403 {
3404 Lisp_Object absname;
3405 struct stat st;
3406 Lisp_Object handler;
3407
3408 absname = expand_and_dir_to_file (filename, current_buffer->directory);
3409
3410 /* If the file name has special constructs in it,
3411 call the corresponding file handler. */
3412 handler = Ffind_file_name_handler (absname, Qfile_modes);
3413 if (!NILP (handler))
3414 return call2 (handler, Qfile_modes, absname);
3415
3416 absname = ENCODE_FILE (absname);
3417
3418 if (stat (SDATA (absname), &st) < 0)
3419 return Qnil;
3420 #if defined (MSDOS) && __DJGPP__ < 2
3421 if (check_executable (SDATA (absname)))
3422 st.st_mode |= S_IEXEC;
3423 #endif /* MSDOS && __DJGPP__ < 2 */
3424
3425 return make_number (st.st_mode & 07777);
3426 }
3427
3428 DEFUN ("set-file-modes", Fset_file_modes, Sset_file_modes, 2, 2, 0,
3429 doc: /* Set mode bits of file named FILENAME to MODE (an integer).
3430 Only the 12 low bits of MODE are used. */)
3431 (filename, mode)
3432 Lisp_Object filename, mode;
3433 {
3434 Lisp_Object absname, encoded_absname;
3435 Lisp_Object handler;
3436
3437 absname = Fexpand_file_name (filename, current_buffer->directory);
3438 CHECK_NUMBER (mode);
3439
3440 /* If the file name has special constructs in it,
3441 call the corresponding file handler. */
3442 handler = Ffind_file_name_handler (absname, Qset_file_modes);
3443 if (!NILP (handler))
3444 return call3 (handler, Qset_file_modes, absname, mode);
3445
3446 encoded_absname = ENCODE_FILE (absname);
3447
3448 if (chmod (SDATA (encoded_absname), XINT (mode)) < 0)
3449 report_file_error ("Doing chmod", Fcons (absname, Qnil));
3450
3451 return Qnil;
3452 }
3453
3454 DEFUN ("set-default-file-modes", Fset_default_file_modes, Sset_default_file_modes, 1, 1, 0,
3455 doc: /* Set the file permission bits for newly created files.
3456 The argument MODE should be an integer; only the low 9 bits are used.
3457 This setting is inherited by subprocesses. */)
3458 (mode)
3459 Lisp_Object mode;
3460 {
3461 CHECK_NUMBER (mode);
3462
3463 umask ((~ XINT (mode)) & 0777);
3464
3465 return Qnil;
3466 }
3467
3468 DEFUN ("default-file-modes", Fdefault_file_modes, Sdefault_file_modes, 0, 0, 0,
3469 doc: /* Return the default file protection for created files.
3470 The value is an integer. */)
3471 ()
3472 {
3473 int realmask;
3474 Lisp_Object value;
3475
3476 realmask = umask (0);
3477 umask (realmask);
3478
3479 XSETINT (value, (~ realmask) & 0777);
3480 return value;
3481 }
3482 \f
3483 extern int lisp_time_argument P_ ((Lisp_Object, time_t *, int *));
3484
3485 DEFUN ("set-file-times", Fset_file_times, Sset_file_times, 1, 2, 0,
3486 doc: /* Set times of file FILENAME to TIME.
3487 Set both access and modification times.
3488 Return t on success, else nil.
3489 Use the current time if TIME is nil. TIME is in the format of
3490 `current-time'. */)
3491 (filename, time)
3492 Lisp_Object filename, time;
3493 {
3494 Lisp_Object absname, encoded_absname;
3495 Lisp_Object handler;
3496 time_t sec;
3497 int usec;
3498
3499 if (! lisp_time_argument (time, &sec, &usec))
3500 error ("Invalid time specification");
3501
3502 absname = Fexpand_file_name (filename, current_buffer->directory);
3503
3504 /* If the file name has special constructs in it,
3505 call the corresponding file handler. */
3506 handler = Ffind_file_name_handler (absname, Qset_file_times);
3507 if (!NILP (handler))
3508 return call3 (handler, Qset_file_times, absname, time);
3509
3510 encoded_absname = ENCODE_FILE (absname);
3511
3512 {
3513 EMACS_TIME t;
3514
3515 EMACS_SET_SECS (t, sec);
3516 EMACS_SET_USECS (t, usec);
3517
3518 if (set_file_times (SDATA (encoded_absname), t, t))
3519 {
3520 #ifdef DOS_NT
3521 struct stat st;
3522
3523 /* Setting times on a directory always fails. */
3524 if (stat (SDATA (encoded_absname), &st) == 0
3525 && (st.st_mode & S_IFMT) == S_IFDIR)
3526 return Qnil;
3527 #endif
3528 report_file_error ("Setting file times", Fcons (absname, Qnil));
3529 return Qnil;
3530 }
3531 }
3532
3533 return Qt;
3534 }
3535 \f
3536 #ifdef __NetBSD__
3537 #define unix 42
3538 #endif
3539
3540 #ifdef unix
3541 DEFUN ("unix-sync", Funix_sync, Sunix_sync, 0, 0, "",
3542 doc: /* Tell Unix to finish all pending disk updates. */)
3543 ()
3544 {
3545 sync ();
3546 return Qnil;
3547 }
3548
3549 #endif /* unix */
3550
3551 DEFUN ("file-newer-than-file-p", Ffile_newer_than_file_p, Sfile_newer_than_file_p, 2, 2, 0,
3552 doc: /* Return t if file FILE1 is newer than file FILE2.
3553 If FILE1 does not exist, the answer is nil;
3554 otherwise, if FILE2 does not exist, the answer is t. */)
3555 (file1, file2)
3556 Lisp_Object file1, file2;
3557 {
3558 Lisp_Object absname1, absname2;
3559 struct stat st;
3560 int mtime1;
3561 Lisp_Object handler;
3562 struct gcpro gcpro1, gcpro2;
3563
3564 CHECK_STRING (file1);
3565 CHECK_STRING (file2);
3566
3567 absname1 = Qnil;
3568 GCPRO2 (absname1, file2);
3569 absname1 = expand_and_dir_to_file (file1, current_buffer->directory);
3570 absname2 = expand_and_dir_to_file (file2, current_buffer->directory);
3571 UNGCPRO;
3572
3573 /* If the file name has special constructs in it,
3574 call the corresponding file handler. */
3575 handler = Ffind_file_name_handler (absname1, Qfile_newer_than_file_p);
3576 if (NILP (handler))
3577 handler = Ffind_file_name_handler (absname2, Qfile_newer_than_file_p);
3578 if (!NILP (handler))
3579 return call3 (handler, Qfile_newer_than_file_p, absname1, absname2);
3580
3581 GCPRO2 (absname1, absname2);
3582 absname1 = ENCODE_FILE (absname1);
3583 absname2 = ENCODE_FILE (absname2);
3584 UNGCPRO;
3585
3586 if (stat (SDATA (absname1), &st) < 0)
3587 return Qnil;
3588
3589 mtime1 = st.st_mtime;
3590
3591 if (stat (SDATA (absname2), &st) < 0)
3592 return Qt;
3593
3594 return (mtime1 > st.st_mtime) ? Qt : Qnil;
3595 }
3596 \f
3597 #ifdef DOS_NT
3598 Lisp_Object Qfind_buffer_file_type;
3599 #endif /* DOS_NT */
3600
3601 #ifndef READ_BUF_SIZE
3602 #define READ_BUF_SIZE (64 << 10)
3603 #endif
3604
3605 extern void adjust_markers_for_delete P_ ((int, int, int, int));
3606
3607 /* This function is called after Lisp functions to decide a coding
3608 system are called, or when they cause an error. Before they are
3609 called, the current buffer is set unibyte and it contains only a
3610 newly inserted text (thus the buffer was empty before the
3611 insertion).
3612
3613 The functions may set markers, overlays, text properties, or even
3614 alter the buffer contents, change the current buffer.
3615
3616 Here, we reset all those changes by:
3617 o set back the current buffer.
3618 o move all markers and overlays to BEG.
3619 o remove all text properties.
3620 o set back the buffer multibyteness. */
3621
3622 static Lisp_Object
3623 decide_coding_unwind (unwind_data)
3624 Lisp_Object unwind_data;
3625 {
3626 Lisp_Object multibyte, undo_list, buffer;
3627
3628 multibyte = XCAR (unwind_data);
3629 unwind_data = XCDR (unwind_data);
3630 undo_list = XCAR (unwind_data);
3631 buffer = XCDR (unwind_data);
3632
3633 if (current_buffer != XBUFFER (buffer))
3634 set_buffer_internal (XBUFFER (buffer));
3635 adjust_markers_for_delete (BEG, BEG_BYTE, Z, Z_BYTE);
3636 adjust_overlays_for_delete (BEG, Z - BEG);
3637 BUF_INTERVALS (current_buffer) = 0;
3638 TEMP_SET_PT_BOTH (BEG, BEG_BYTE);
3639
3640 /* Now we are safe to change the buffer's multibyteness directly. */
3641 current_buffer->enable_multibyte_characters = multibyte;
3642 current_buffer->undo_list = undo_list;
3643
3644 return Qnil;
3645 }
3646
3647
3648 /* Used to pass values from insert-file-contents to read_non_regular. */
3649
3650 static int non_regular_fd;
3651 static int non_regular_inserted;
3652 static int non_regular_nbytes;
3653
3654
3655 /* Read from a non-regular file.
3656 Read non_regular_trytry bytes max from non_regular_fd.
3657 Non_regular_inserted specifies where to put the read bytes.
3658 Value is the number of bytes read. */
3659
3660 static Lisp_Object
3661 read_non_regular ()
3662 {
3663 int nbytes;
3664
3665 immediate_quit = 1;
3666 QUIT;
3667 nbytes = emacs_read (non_regular_fd,
3668 BEG_ADDR + PT_BYTE - BEG_BYTE + non_regular_inserted,
3669 non_regular_nbytes);
3670 immediate_quit = 0;
3671 return make_number (nbytes);
3672 }
3673
3674
3675 /* Condition-case handler used when reading from non-regular files
3676 in insert-file-contents. */
3677
3678 static Lisp_Object
3679 read_non_regular_quit ()
3680 {
3681 return Qnil;
3682 }
3683
3684
3685 DEFUN ("insert-file-contents", Finsert_file_contents, Sinsert_file_contents,
3686 1, 5, 0,
3687 doc: /* Insert contents of file FILENAME after point.
3688 Returns list of absolute file name and number of characters inserted.
3689 If second argument VISIT is non-nil, the buffer's visited filename
3690 and last save file modtime are set, and it is marked unmodified.
3691 If visiting and the file does not exist, visiting is completed
3692 before the error is signaled.
3693 The optional third and fourth arguments BEG and END
3694 specify what portion of the file to insert.
3695 These arguments count bytes in the file, not characters in the buffer.
3696 If VISIT is non-nil, BEG and END must be nil.
3697
3698 If optional fifth argument REPLACE is non-nil,
3699 it means replace the current buffer contents (in the accessible portion)
3700 with the file contents. This is better than simply deleting and inserting
3701 the whole thing because (1) it preserves some marker positions
3702 and (2) it puts less data in the undo list.
3703 When REPLACE is non-nil, the value is the number of characters actually read,
3704 which is often less than the number of characters to be read.
3705
3706 This does code conversion according to the value of
3707 `coding-system-for-read' or `file-coding-system-alist',
3708 and sets the variable `last-coding-system-used' to the coding system
3709 actually used. */)
3710 (filename, visit, beg, end, replace)
3711 Lisp_Object filename, visit, beg, end, replace;
3712 {
3713 struct stat st;
3714 register int fd;
3715 int inserted = 0;
3716 register int how_much;
3717 register int unprocessed;
3718 int count = SPECPDL_INDEX ();
3719 struct gcpro gcpro1, gcpro2, gcpro3, gcpro4;
3720 Lisp_Object handler, val, insval, orig_filename;
3721 Lisp_Object p;
3722 int total = 0;
3723 int not_regular = 0;
3724 unsigned char read_buf[READ_BUF_SIZE];
3725 struct coding_system coding;
3726 unsigned char buffer[1 << 14];
3727 int replace_handled = 0;
3728 int set_coding_system = 0;
3729 int coding_system_decided = 0;
3730 int read_quit = 0;
3731
3732 if (current_buffer->base_buffer && ! NILP (visit))
3733 error ("Cannot do file visiting in an indirect buffer");
3734
3735 if (!NILP (current_buffer->read_only))
3736 Fbarf_if_buffer_read_only ();
3737
3738 val = Qnil;
3739 p = Qnil;
3740 orig_filename = Qnil;
3741
3742 GCPRO4 (filename, val, p, orig_filename);
3743
3744 CHECK_STRING (filename);
3745 filename = Fexpand_file_name (filename, Qnil);
3746
3747 /* If the file name has special constructs in it,
3748 call the corresponding file handler. */
3749 handler = Ffind_file_name_handler (filename, Qinsert_file_contents);
3750 if (!NILP (handler))
3751 {
3752 val = call6 (handler, Qinsert_file_contents, filename,
3753 visit, beg, end, replace);
3754 if (CONSP (val) && CONSP (XCDR (val)))
3755 inserted = XINT (XCAR (XCDR (val)));
3756 goto handled;
3757 }
3758
3759 orig_filename = filename;
3760 filename = ENCODE_FILE (filename);
3761
3762 fd = -1;
3763
3764 #ifdef WINDOWSNT
3765 {
3766 Lisp_Object tem = Vw32_get_true_file_attributes;
3767
3768 /* Tell stat to use expensive method to get accurate info. */
3769 Vw32_get_true_file_attributes = Qt;
3770 total = stat (SDATA (filename), &st);
3771 Vw32_get_true_file_attributes = tem;
3772 }
3773 if (total < 0)
3774 #else
3775 #ifndef APOLLO
3776 if (stat (SDATA (filename), &st) < 0)
3777 #else
3778 if ((fd = emacs_open (SDATA (filename), O_RDONLY, 0)) < 0
3779 || fstat (fd, &st) < 0)
3780 #endif /* not APOLLO */
3781 #endif /* WINDOWSNT */
3782 {
3783 if (fd >= 0) emacs_close (fd);
3784 badopen:
3785 if (NILP (visit))
3786 report_file_error ("Opening input file", Fcons (orig_filename, Qnil));
3787 st.st_mtime = -1;
3788 how_much = 0;
3789 if (!NILP (Vcoding_system_for_read))
3790 Fset (Qbuffer_file_coding_system, Vcoding_system_for_read);
3791 goto notfound;
3792 }
3793
3794 #ifdef S_IFREG
3795 /* This code will need to be changed in order to work on named
3796 pipes, and it's probably just not worth it. So we should at
3797 least signal an error. */
3798 if (!S_ISREG (st.st_mode))
3799 {
3800 not_regular = 1;
3801
3802 if (! NILP (visit))
3803 goto notfound;
3804
3805 if (! NILP (replace) || ! NILP (beg) || ! NILP (end))
3806 Fsignal (Qfile_error,
3807 Fcons (build_string ("not a regular file"),
3808 Fcons (orig_filename, Qnil)));
3809 }
3810 #endif
3811
3812 if (fd < 0)
3813 if ((fd = emacs_open (SDATA (filename), O_RDONLY, 0)) < 0)
3814 goto badopen;
3815
3816 /* Replacement should preserve point as it preserves markers. */
3817 if (!NILP (replace))
3818 record_unwind_protect (restore_point_unwind, Fpoint_marker ());
3819
3820 record_unwind_protect (close_file_unwind, make_number (fd));
3821
3822 /* Supposedly happens on VMS. */
3823 /* Can happen on any platform that uses long as type of off_t, but allows
3824 file sizes to exceed 2Gb. VMS is no longer officially supported, so
3825 give a message suitable for the latter case. */
3826 if (! not_regular && st.st_size < 0)
3827 error ("Maximum buffer size exceeded");
3828
3829 /* Prevent redisplay optimizations. */
3830 current_buffer->clip_changed = 1;
3831
3832 if (!NILP (visit))
3833 {
3834 if (!NILP (beg) || !NILP (end))
3835 error ("Attempt to visit less than an entire file");
3836 if (BEG < Z && NILP (replace))
3837 error ("Cannot do file visiting in a non-empty buffer");
3838 }
3839
3840 if (!NILP (beg))
3841 CHECK_NUMBER (beg);
3842 else
3843 XSETFASTINT (beg, 0);
3844
3845 if (!NILP (end))
3846 CHECK_NUMBER (end);
3847 else
3848 {
3849 if (! not_regular)
3850 {
3851 XSETINT (end, st.st_size);
3852
3853 /* Arithmetic overflow can occur if an Emacs integer cannot
3854 represent the file size, or if the calculations below
3855 overflow. The calculations below double the file size
3856 twice, so check that it can be multiplied by 4 safely. */
3857 if (XINT (end) != st.st_size
3858 || ((int) st.st_size * 4) / 4 != st.st_size)
3859 error ("Maximum buffer size exceeded");
3860
3861 /* The file size returned from stat may be zero, but data
3862 may be readable nonetheless, for example when this is a
3863 file in the /proc filesystem. */
3864 if (st.st_size == 0)
3865 XSETINT (end, READ_BUF_SIZE);
3866 }
3867 }
3868
3869 if (EQ (Vcoding_system_for_read, Qauto_save_coding))
3870 {
3871 /* We use emacs-mule for auto saving... */
3872 setup_coding_system (Qemacs_mule, &coding);
3873 /* ... but with the special flag to indicate to read in a
3874 multibyte sequence for eight-bit-control char as is. */
3875 coding.flags = 1;
3876 coding.src_multibyte = 0;
3877 coding.dst_multibyte
3878 = !NILP (current_buffer->enable_multibyte_characters);
3879 coding.eol_type = CODING_EOL_LF;
3880 coding_system_decided = 1;
3881 }
3882 else if (BEG < Z)
3883 {
3884 /* Decide the coding system to use for reading the file now
3885 because we can't use an optimized method for handling
3886 `coding:' tag if the current buffer is not empty. */
3887 Lisp_Object val;
3888 val = Qnil;
3889
3890 if (!NILP (Vcoding_system_for_read))
3891 val = Vcoding_system_for_read;
3892 else
3893 {
3894 /* Don't try looking inside a file for a coding system
3895 specification if it is not seekable. */
3896 if (! not_regular && ! NILP (Vset_auto_coding_function))
3897 {
3898 /* Find a coding system specified in the heading two
3899 lines or in the tailing several lines of the file.
3900 We assume that the 1K-byte and 3K-byte for heading
3901 and tailing respectively are sufficient for this
3902 purpose. */
3903 int nread;
3904
3905 if (st.st_size <= (1024 * 4))
3906 nread = emacs_read (fd, read_buf, 1024 * 4);
3907 else
3908 {
3909 nread = emacs_read (fd, read_buf, 1024);
3910 if (nread >= 0)
3911 {
3912 if (lseek (fd, st.st_size - (1024 * 3), 0) < 0)
3913 report_file_error ("Setting file position",
3914 Fcons (orig_filename, Qnil));
3915 nread += emacs_read (fd, read_buf + nread, 1024 * 3);
3916 }
3917 }
3918
3919 if (nread < 0)
3920 error ("IO error reading %s: %s",
3921 SDATA (orig_filename), emacs_strerror (errno));
3922 else if (nread > 0)
3923 {
3924 struct buffer *prev = current_buffer;
3925 Lisp_Object buffer;
3926 struct buffer *buf;
3927
3928 record_unwind_protect (Fset_buffer, Fcurrent_buffer ());
3929
3930 buffer = Fget_buffer_create (build_string (" *code-converting-work*"));
3931 buf = XBUFFER (buffer);
3932
3933 delete_all_overlays (buf);
3934 buf->directory = current_buffer->directory;
3935 buf->read_only = Qnil;
3936 buf->filename = Qnil;
3937 buf->undo_list = Qt;
3938 eassert (buf->overlays_before == NULL);
3939 eassert (buf->overlays_after == NULL);
3940
3941 set_buffer_internal (buf);
3942 Ferase_buffer ();
3943 buf->enable_multibyte_characters = Qnil;
3944
3945 insert_1_both (read_buf, nread, nread, 0, 0, 0);
3946 TEMP_SET_PT_BOTH (BEG, BEG_BYTE);
3947 val = call2 (Vset_auto_coding_function,
3948 filename, make_number (nread));
3949 set_buffer_internal (prev);
3950
3951 /* Discard the unwind protect for recovering the
3952 current buffer. */
3953 specpdl_ptr--;
3954
3955 /* Rewind the file for the actual read done later. */
3956 if (lseek (fd, 0, 0) < 0)
3957 report_file_error ("Setting file position",
3958 Fcons (orig_filename, Qnil));
3959 }
3960 }
3961
3962 if (NILP (val))
3963 {
3964 /* If we have not yet decided a coding system, check
3965 file-coding-system-alist. */
3966 Lisp_Object args[6], coding_systems;
3967
3968 args[0] = Qinsert_file_contents, args[1] = orig_filename;
3969 args[2] = visit, args[3] = beg, args[4] = end, args[5] = replace;
3970 coding_systems = Ffind_operation_coding_system (6, args);
3971 if (CONSP (coding_systems))
3972 val = XCAR (coding_systems);
3973 }
3974 }
3975
3976 setup_coding_system (Fcheck_coding_system (val), &coding);
3977 /* Ensure we set Vlast_coding_system_used. */
3978 set_coding_system = 1;
3979
3980 if (NILP (current_buffer->enable_multibyte_characters)
3981 && ! NILP (val))
3982 /* We must suppress all character code conversion except for
3983 end-of-line conversion. */
3984 setup_raw_text_coding_system (&coding);
3985
3986 coding.src_multibyte = 0;
3987 coding.dst_multibyte
3988 = !NILP (current_buffer->enable_multibyte_characters);
3989 coding_system_decided = 1;
3990 }
3991
3992 /* If requested, replace the accessible part of the buffer
3993 with the file contents. Avoid replacing text at the
3994 beginning or end of the buffer that matches the file contents;
3995 that preserves markers pointing to the unchanged parts.
3996
3997 Here we implement this feature in an optimized way
3998 for the case where code conversion is NOT needed.
3999 The following if-statement handles the case of conversion
4000 in a less optimal way.
4001
4002 If the code conversion is "automatic" then we try using this
4003 method and hope for the best.
4004 But if we discover the need for conversion, we give up on this method
4005 and let the following if-statement handle the replace job. */
4006 if (!NILP (replace)
4007 && BEGV < ZV
4008 && !(coding.common_flags & CODING_REQUIRE_DECODING_MASK))
4009 {
4010 /* same_at_start and same_at_end count bytes,
4011 because file access counts bytes
4012 and BEG and END count bytes. */
4013 int same_at_start = BEGV_BYTE;
4014 int same_at_end = ZV_BYTE;
4015 int overlap;
4016 /* There is still a possibility we will find the need to do code
4017 conversion. If that happens, we set this variable to 1 to
4018 give up on handling REPLACE in the optimized way. */
4019 int giveup_match_end = 0;
4020
4021 if (XINT (beg) != 0)
4022 {
4023 if (lseek (fd, XINT (beg), 0) < 0)
4024 report_file_error ("Setting file position",
4025 Fcons (orig_filename, Qnil));
4026 }
4027
4028 immediate_quit = 1;
4029 QUIT;
4030 /* Count how many chars at the start of the file
4031 match the text at the beginning of the buffer. */
4032 while (1)
4033 {
4034 int nread, bufpos;
4035
4036 nread = emacs_read (fd, buffer, sizeof buffer);
4037 if (nread < 0)
4038 error ("IO error reading %s: %s",
4039 SDATA (orig_filename), emacs_strerror (errno));
4040 else if (nread == 0)
4041 break;
4042
4043 if (coding.type == coding_type_undecided)
4044 detect_coding (&coding, buffer, nread);
4045 if (coding.common_flags & CODING_REQUIRE_DECODING_MASK)
4046 /* We found that the file should be decoded somehow.
4047 Let's give up here. */
4048 {
4049 giveup_match_end = 1;
4050 break;
4051 }
4052
4053 if (coding.eol_type == CODING_EOL_UNDECIDED)
4054 detect_eol (&coding, buffer, nread);
4055 if (coding.eol_type != CODING_EOL_UNDECIDED
4056 && coding.eol_type != CODING_EOL_LF)
4057 /* We found that the format of eol should be decoded.
4058 Let's give up here. */
4059 {
4060 giveup_match_end = 1;
4061 break;
4062 }
4063
4064 bufpos = 0;
4065 while (bufpos < nread && same_at_start < ZV_BYTE
4066 && FETCH_BYTE (same_at_start) == buffer[bufpos])
4067 same_at_start++, bufpos++;
4068 /* If we found a discrepancy, stop the scan.
4069 Otherwise loop around and scan the next bufferful. */
4070 if (bufpos != nread)
4071 break;
4072 }
4073 immediate_quit = 0;
4074 /* If the file matches the buffer completely,
4075 there's no need to replace anything. */
4076 if (same_at_start - BEGV_BYTE == XINT (end))
4077 {
4078 emacs_close (fd);
4079 specpdl_ptr--;
4080 /* Truncate the buffer to the size of the file. */
4081 del_range_1 (same_at_start, same_at_end, 0, 0);
4082 goto handled;
4083 }
4084 immediate_quit = 1;
4085 QUIT;
4086 /* Count how many chars at the end of the file
4087 match the text at the end of the buffer. But, if we have
4088 already found that decoding is necessary, don't waste time. */
4089 while (!giveup_match_end)
4090 {
4091 int total_read, nread, bufpos, curpos, trial;
4092
4093 /* At what file position are we now scanning? */
4094 curpos = XINT (end) - (ZV_BYTE - same_at_end);
4095 /* If the entire file matches the buffer tail, stop the scan. */
4096 if (curpos == 0)
4097 break;
4098 /* How much can we scan in the next step? */
4099 trial = min (curpos, sizeof buffer);
4100 if (lseek (fd, curpos - trial, 0) < 0)
4101 report_file_error ("Setting file position",
4102 Fcons (orig_filename, Qnil));
4103
4104 total_read = nread = 0;
4105 while (total_read < trial)
4106 {
4107 nread = emacs_read (fd, buffer + total_read, trial - total_read);
4108 if (nread < 0)
4109 error ("IO error reading %s: %s",
4110 SDATA (orig_filename), emacs_strerror (errno));
4111 else if (nread == 0)
4112 break;
4113 total_read += nread;
4114 }
4115
4116 /* Scan this bufferful from the end, comparing with
4117 the Emacs buffer. */
4118 bufpos = total_read;
4119
4120 /* Compare with same_at_start to avoid counting some buffer text
4121 as matching both at the file's beginning and at the end. */
4122 while (bufpos > 0 && same_at_end > same_at_start
4123 && FETCH_BYTE (same_at_end - 1) == buffer[bufpos - 1])
4124 same_at_end--, bufpos--;
4125
4126 /* If we found a discrepancy, stop the scan.
4127 Otherwise loop around and scan the preceding bufferful. */
4128 if (bufpos != 0)
4129 {
4130 /* If this discrepancy is because of code conversion,
4131 we cannot use this method; giveup and try the other. */
4132 if (same_at_end > same_at_start
4133 && FETCH_BYTE (same_at_end - 1) >= 0200
4134 && ! NILP (current_buffer->enable_multibyte_characters)
4135 && (CODING_MAY_REQUIRE_DECODING (&coding)))
4136 giveup_match_end = 1;
4137 break;
4138 }
4139
4140 if (nread == 0)
4141 break;
4142 }
4143 immediate_quit = 0;
4144
4145 if (! giveup_match_end)
4146 {
4147 int temp;
4148
4149 /* We win! We can handle REPLACE the optimized way. */
4150
4151 /* Extend the start of non-matching text area to multibyte
4152 character boundary. */
4153 if (! NILP (current_buffer->enable_multibyte_characters))
4154 while (same_at_start > BEGV_BYTE
4155 && ! CHAR_HEAD_P (FETCH_BYTE (same_at_start)))
4156 same_at_start--;
4157
4158 /* Extend the end of non-matching text area to multibyte
4159 character boundary. */
4160 if (! NILP (current_buffer->enable_multibyte_characters))
4161 while (same_at_end < ZV_BYTE
4162 && ! CHAR_HEAD_P (FETCH_BYTE (same_at_end)))
4163 same_at_end++;
4164
4165 /* Don't try to reuse the same piece of text twice. */
4166 overlap = (same_at_start - BEGV_BYTE
4167 - (same_at_end + st.st_size - ZV));
4168 if (overlap > 0)
4169 same_at_end += overlap;
4170
4171 /* Arrange to read only the nonmatching middle part of the file. */
4172 XSETFASTINT (beg, XINT (beg) + (same_at_start - BEGV_BYTE));
4173 XSETFASTINT (end, XINT (end) - (ZV_BYTE - same_at_end));
4174
4175 del_range_byte (same_at_start, same_at_end, 0);
4176 /* Insert from the file at the proper position. */
4177 temp = BYTE_TO_CHAR (same_at_start);
4178 SET_PT_BOTH (temp, same_at_start);
4179
4180 /* If display currently starts at beginning of line,
4181 keep it that way. */
4182 if (XBUFFER (XWINDOW (selected_window)->buffer) == current_buffer)
4183 XWINDOW (selected_window)->start_at_line_beg = Fbolp ();
4184
4185 replace_handled = 1;
4186 }
4187 }
4188
4189 /* If requested, replace the accessible part of the buffer
4190 with the file contents. Avoid replacing text at the
4191 beginning or end of the buffer that matches the file contents;
4192 that preserves markers pointing to the unchanged parts.
4193
4194 Here we implement this feature for the case where code conversion
4195 is needed, in a simple way that needs a lot of memory.
4196 The preceding if-statement handles the case of no conversion
4197 in a more optimized way. */
4198 if (!NILP (replace) && ! replace_handled && BEGV < ZV)
4199 {
4200 int same_at_start = BEGV_BYTE;
4201 int same_at_end = ZV_BYTE;
4202 int overlap;
4203 int bufpos;
4204 /* Make sure that the gap is large enough. */
4205 int bufsize = 2 * st.st_size;
4206 unsigned char *conversion_buffer = (unsigned char *) xmalloc (bufsize);
4207 int temp;
4208
4209 /* First read the whole file, performing code conversion into
4210 CONVERSION_BUFFER. */
4211
4212 if (lseek (fd, XINT (beg), 0) < 0)
4213 {
4214 xfree (conversion_buffer);
4215 report_file_error ("Setting file position",
4216 Fcons (orig_filename, Qnil));
4217 }
4218
4219 total = st.st_size; /* Total bytes in the file. */
4220 how_much = 0; /* Bytes read from file so far. */
4221 inserted = 0; /* Bytes put into CONVERSION_BUFFER so far. */
4222 unprocessed = 0; /* Bytes not processed in previous loop. */
4223
4224 while (how_much < total)
4225 {
4226 /* try is reserved in some compilers (Microsoft C) */
4227 int trytry = min (total - how_much, READ_BUF_SIZE - unprocessed);
4228 unsigned char *destination = read_buf + unprocessed;
4229 int this;
4230
4231 /* Allow quitting out of the actual I/O. */
4232 immediate_quit = 1;
4233 QUIT;
4234 this = emacs_read (fd, destination, trytry);
4235 immediate_quit = 0;
4236
4237 if (this < 0 || this + unprocessed == 0)
4238 {
4239 how_much = this;
4240 break;
4241 }
4242
4243 how_much += this;
4244
4245 if (CODING_MAY_REQUIRE_DECODING (&coding))
4246 {
4247 int require, result;
4248
4249 this += unprocessed;
4250
4251 /* If we are using more space than estimated,
4252 make CONVERSION_BUFFER bigger. */
4253 require = decoding_buffer_size (&coding, this);
4254 if (inserted + require + 2 * (total - how_much) > bufsize)
4255 {
4256 bufsize = inserted + require + 2 * (total - how_much);
4257 conversion_buffer = (unsigned char *) xrealloc (conversion_buffer, bufsize);
4258 }
4259
4260 /* Convert this batch with results in CONVERSION_BUFFER. */
4261 if (how_much >= total) /* This is the last block. */
4262 coding.mode |= CODING_MODE_LAST_BLOCK;
4263 if (coding.composing != COMPOSITION_DISABLED)
4264 coding_allocate_composition_data (&coding, BEGV);
4265 result = decode_coding (&coding, read_buf,
4266 conversion_buffer + inserted,
4267 this, bufsize - inserted);
4268
4269 /* Save for next iteration whatever we didn't convert. */
4270 unprocessed = this - coding.consumed;
4271 bcopy (read_buf + coding.consumed, read_buf, unprocessed);
4272 if (!NILP (current_buffer->enable_multibyte_characters))
4273 this = coding.produced;
4274 else
4275 this = str_as_unibyte (conversion_buffer + inserted,
4276 coding.produced);
4277 }
4278
4279 inserted += this;
4280 }
4281
4282 /* At this point, INSERTED is how many characters (i.e. bytes)
4283 are present in CONVERSION_BUFFER.
4284 HOW_MUCH should equal TOTAL,
4285 or should be <= 0 if we couldn't read the file. */
4286
4287 if (how_much < 0)
4288 {
4289 xfree (conversion_buffer);
4290 coding_free_composition_data (&coding);
4291 if (how_much == -1)
4292 error ("IO error reading %s: %s",
4293 SDATA (orig_filename), emacs_strerror (errno));
4294 else if (how_much == -2)
4295 error ("maximum buffer size exceeded");
4296 }
4297
4298 /* Compare the beginning of the converted file
4299 with the buffer text. */
4300
4301 bufpos = 0;
4302 while (bufpos < inserted && same_at_start < same_at_end
4303 && FETCH_BYTE (same_at_start) == conversion_buffer[bufpos])
4304 same_at_start++, bufpos++;
4305
4306 /* If the file matches the buffer completely,
4307 there's no need to replace anything. */
4308
4309 if (bufpos == inserted)
4310 {
4311 xfree (conversion_buffer);
4312 coding_free_composition_data (&coding);
4313 emacs_close (fd);
4314 specpdl_ptr--;
4315 /* Truncate the buffer to the size of the file. */
4316 del_range_byte (same_at_start, same_at_end, 0);
4317 inserted = 0;
4318 goto handled;
4319 }
4320
4321 /* Extend the start of non-matching text area to multibyte
4322 character boundary. */
4323 if (! NILP (current_buffer->enable_multibyte_characters))
4324 while (same_at_start > BEGV_BYTE
4325 && ! CHAR_HEAD_P (FETCH_BYTE (same_at_start)))
4326 same_at_start--;
4327
4328 /* Scan this bufferful from the end, comparing with
4329 the Emacs buffer. */
4330 bufpos = inserted;
4331
4332 /* Compare with same_at_start to avoid counting some buffer text
4333 as matching both at the file's beginning and at the end. */
4334 while (bufpos > 0 && same_at_end > same_at_start
4335 && FETCH_BYTE (same_at_end - 1) == conversion_buffer[bufpos - 1])
4336 same_at_end--, bufpos--;
4337
4338 /* Extend the end of non-matching text area to multibyte
4339 character boundary. */
4340 if (! NILP (current_buffer->enable_multibyte_characters))
4341 while (same_at_end < ZV_BYTE
4342 && ! CHAR_HEAD_P (FETCH_BYTE (same_at_end)))
4343 same_at_end++;
4344
4345 /* Don't try to reuse the same piece of text twice. */
4346 overlap = same_at_start - BEGV_BYTE - (same_at_end + inserted - ZV_BYTE);
4347 if (overlap > 0)
4348 same_at_end += overlap;
4349
4350 /* If display currently starts at beginning of line,
4351 keep it that way. */
4352 if (XBUFFER (XWINDOW (selected_window)->buffer) == current_buffer)
4353 XWINDOW (selected_window)->start_at_line_beg = Fbolp ();
4354
4355 /* Replace the chars that we need to replace,
4356 and update INSERTED to equal the number of bytes
4357 we are taking from the file. */
4358 inserted -= (ZV_BYTE - same_at_end) + (same_at_start - BEGV_BYTE);
4359
4360 if (same_at_end != same_at_start)
4361 {
4362 del_range_byte (same_at_start, same_at_end, 0);
4363 temp = GPT;
4364 same_at_start = GPT_BYTE;
4365 }
4366 else
4367 {
4368 temp = BYTE_TO_CHAR (same_at_start);
4369 }
4370 /* Insert from the file at the proper position. */
4371 SET_PT_BOTH (temp, same_at_start);
4372 insert_1 (conversion_buffer + same_at_start - BEGV_BYTE, inserted,
4373 0, 0, 0);
4374 if (coding.cmp_data && coding.cmp_data->used)
4375 coding_restore_composition (&coding, Fcurrent_buffer ());
4376 coding_free_composition_data (&coding);
4377
4378 /* Set `inserted' to the number of inserted characters. */
4379 inserted = PT - temp;
4380
4381 xfree (conversion_buffer);
4382 emacs_close (fd);
4383 specpdl_ptr--;
4384
4385 goto handled;
4386 }
4387
4388 if (! not_regular)
4389 {
4390 register Lisp_Object temp;
4391
4392 total = XINT (end) - XINT (beg);
4393
4394 /* Make sure point-max won't overflow after this insertion. */
4395 XSETINT (temp, total);
4396 if (total != XINT (temp))
4397 error ("Maximum buffer size exceeded");
4398 }
4399 else
4400 /* For a special file, all we can do is guess. */
4401 total = READ_BUF_SIZE;
4402
4403 if (NILP (visit) && total > 0)
4404 prepare_to_modify_buffer (PT, PT, NULL);
4405
4406 move_gap (PT);
4407 if (GAP_SIZE < total)
4408 make_gap (total - GAP_SIZE);
4409
4410 if (XINT (beg) != 0 || !NILP (replace))
4411 {
4412 if (lseek (fd, XINT (beg), 0) < 0)
4413 report_file_error ("Setting file position",
4414 Fcons (orig_filename, Qnil));
4415 }
4416
4417 /* In the following loop, HOW_MUCH contains the total bytes read so
4418 far for a regular file, and not changed for a special file. But,
4419 before exiting the loop, it is set to a negative value if I/O
4420 error occurs. */
4421 how_much = 0;
4422
4423 /* Total bytes inserted. */
4424 inserted = 0;
4425
4426 /* Here, we don't do code conversion in the loop. It is done by
4427 code_convert_region after all data are read into the buffer. */
4428 {
4429 int gap_size = GAP_SIZE;
4430
4431 while (how_much < total)
4432 {
4433 /* try is reserved in some compilers (Microsoft C) */
4434 int trytry = min (total - how_much, READ_BUF_SIZE);
4435 int this;
4436
4437 if (not_regular)
4438 {
4439 Lisp_Object val;
4440
4441 /* Maybe make more room. */
4442 if (gap_size < trytry)
4443 {
4444 make_gap (total - gap_size);
4445 gap_size = GAP_SIZE;
4446 }
4447
4448 /* Read from the file, capturing `quit'. When an
4449 error occurs, end the loop, and arrange for a quit
4450 to be signaled after decoding the text we read. */
4451 non_regular_fd = fd;
4452 non_regular_inserted = inserted;
4453 non_regular_nbytes = trytry;
4454 val = internal_condition_case_1 (read_non_regular, Qnil, Qerror,
4455 read_non_regular_quit);
4456 if (NILP (val))
4457 {
4458 read_quit = 1;
4459 break;
4460 }
4461
4462 this = XINT (val);
4463 }
4464 else
4465 {
4466 /* Allow quitting out of the actual I/O. We don't make text
4467 part of the buffer until all the reading is done, so a C-g
4468 here doesn't do any harm. */
4469 immediate_quit = 1;
4470 QUIT;
4471 this = emacs_read (fd, BEG_ADDR + PT_BYTE - BEG_BYTE + inserted, trytry);
4472 immediate_quit = 0;
4473 }
4474
4475 if (this <= 0)
4476 {
4477 how_much = this;
4478 break;
4479 }
4480
4481 gap_size -= this;
4482
4483 /* For a regular file, where TOTAL is the real size,
4484 count HOW_MUCH to compare with it.
4485 For a special file, where TOTAL is just a buffer size,
4486 so don't bother counting in HOW_MUCH.
4487 (INSERTED is where we count the number of characters inserted.) */
4488 if (! not_regular)
4489 how_much += this;
4490 inserted += this;
4491 }
4492 }
4493
4494 /* Make the text read part of the buffer. */
4495 GAP_SIZE -= inserted;
4496 GPT += inserted;
4497 GPT_BYTE += inserted;
4498 ZV += inserted;
4499 ZV_BYTE += inserted;
4500 Z += inserted;
4501 Z_BYTE += inserted;
4502
4503 if (GAP_SIZE > 0)
4504 /* Put an anchor to ensure multi-byte form ends at gap. */
4505 *GPT_ADDR = 0;
4506
4507 emacs_close (fd);
4508
4509 /* Discard the unwind protect for closing the file. */
4510 specpdl_ptr--;
4511
4512 if (how_much < 0)
4513 error ("IO error reading %s: %s",
4514 SDATA (orig_filename), emacs_strerror (errno));
4515
4516 notfound:
4517
4518 if (! coding_system_decided)
4519 {
4520 /* The coding system is not yet decided. Decide it by an
4521 optimized method for handling `coding:' tag.
4522
4523 Note that we can get here only if the buffer was empty
4524 before the insertion. */
4525 Lisp_Object val;
4526 val = Qnil;
4527
4528 if (!NILP (Vcoding_system_for_read))
4529 val = Vcoding_system_for_read;
4530 else
4531 {
4532 /* Since we are sure that the current buffer was empty
4533 before the insertion, we can toggle
4534 enable-multibyte-characters directly here without taking
4535 care of marker adjustment and byte combining problem. By
4536 this way, we can run Lisp program safely before decoding
4537 the inserted text. */
4538 Lisp_Object unwind_data;
4539 int count = SPECPDL_INDEX ();
4540
4541 unwind_data = Fcons (current_buffer->enable_multibyte_characters,
4542 Fcons (current_buffer->undo_list,
4543 Fcurrent_buffer ()));
4544 current_buffer->enable_multibyte_characters = Qnil;
4545 current_buffer->undo_list = Qt;
4546 record_unwind_protect (decide_coding_unwind, unwind_data);
4547
4548 if (inserted > 0 && ! NILP (Vset_auto_coding_function))
4549 {
4550 val = call2 (Vset_auto_coding_function,
4551 filename, make_number (inserted));
4552 }
4553
4554 if (NILP (val))
4555 {
4556 /* If the coding system is not yet decided, check
4557 file-coding-system-alist. */
4558 Lisp_Object args[6], coding_systems;
4559
4560 args[0] = Qinsert_file_contents, args[1] = orig_filename;
4561 args[2] = visit, args[3] = beg, args[4] = end, args[5] = Qnil;
4562 coding_systems = Ffind_operation_coding_system (6, args);
4563 if (CONSP (coding_systems))
4564 val = XCAR (coding_systems);
4565 }
4566 unbind_to (count, Qnil);
4567 inserted = Z_BYTE - BEG_BYTE;
4568 }
4569
4570 /* The following kludgy code is to avoid some compiler bug.
4571 We can't simply do
4572 setup_coding_system (val, &coding);
4573 on some system. */
4574 {
4575 struct coding_system temp_coding;
4576 setup_coding_system (Fcheck_coding_system (val), &temp_coding);
4577 bcopy (&temp_coding, &coding, sizeof coding);
4578 }
4579 /* Ensure we set Vlast_coding_system_used. */
4580 set_coding_system = 1;
4581
4582 if (NILP (current_buffer->enable_multibyte_characters)
4583 && ! NILP (val))
4584 /* We must suppress all character code conversion except for
4585 end-of-line conversion. */
4586 setup_raw_text_coding_system (&coding);
4587 coding.src_multibyte = 0;
4588 coding.dst_multibyte
4589 = !NILP (current_buffer->enable_multibyte_characters);
4590 }
4591
4592 if (!NILP (visit)
4593 /* Can't do this if part of the buffer might be preserved. */
4594 && NILP (replace)
4595 && (coding.type == coding_type_no_conversion
4596 || coding.type == coding_type_raw_text))
4597 {
4598 /* Visiting a file with these coding system makes the buffer
4599 unibyte. */
4600 current_buffer->enable_multibyte_characters = Qnil;
4601 coding.dst_multibyte = 0;
4602 }
4603
4604 if (inserted > 0 || coding.type == coding_type_ccl)
4605 {
4606 if (CODING_MAY_REQUIRE_DECODING (&coding))
4607 {
4608 code_convert_region (PT, PT_BYTE, PT + inserted, PT_BYTE + inserted,
4609 &coding, 0, 0);
4610 inserted = coding.produced_char;
4611 }
4612 else
4613 adjust_after_insert (PT, PT_BYTE, PT + inserted, PT_BYTE + inserted,
4614 inserted);
4615 }
4616
4617 /* Now INSERTED is measured in characters. */
4618
4619 #ifdef DOS_NT
4620 /* Use the conversion type to determine buffer-file-type
4621 (find-buffer-file-type is now used to help determine the
4622 conversion). */
4623 if ((coding.eol_type == CODING_EOL_UNDECIDED
4624 || coding.eol_type == CODING_EOL_LF)
4625 && ! CODING_REQUIRE_DECODING (&coding))
4626 current_buffer->buffer_file_type = Qt;
4627 else
4628 current_buffer->buffer_file_type = Qnil;
4629 #endif
4630
4631 handled:
4632
4633 if (!NILP (visit))
4634 {
4635 if (!EQ (current_buffer->undo_list, Qt))
4636 current_buffer->undo_list = Qnil;
4637 #ifdef APOLLO
4638 stat (SDATA (filename), &st);
4639 #endif
4640
4641 if (NILP (handler))
4642 {
4643 current_buffer->modtime = st.st_mtime;
4644 current_buffer->filename = orig_filename;
4645 }
4646
4647 SAVE_MODIFF = MODIFF;
4648 current_buffer->auto_save_modified = MODIFF;
4649 XSETFASTINT (current_buffer->save_length, Z - BEG);
4650 #ifdef CLASH_DETECTION
4651 if (NILP (handler))
4652 {
4653 if (!NILP (current_buffer->file_truename))
4654 unlock_file (current_buffer->file_truename);
4655 unlock_file (filename);
4656 }
4657 #endif /* CLASH_DETECTION */
4658 if (not_regular)
4659 Fsignal (Qfile_error,
4660 Fcons (build_string ("not a regular file"),
4661 Fcons (orig_filename, Qnil)));
4662 }
4663
4664 if (set_coding_system)
4665 Vlast_coding_system_used = coding.symbol;
4666
4667 if (! NILP (Ffboundp (Qafter_insert_file_set_coding)))
4668 {
4669 insval = call2 (Qafter_insert_file_set_coding, make_number (inserted),
4670 visit);
4671 if (! NILP (insval))
4672 {
4673 CHECK_NUMBER (insval);
4674 inserted = XFASTINT (insval);
4675 }
4676 }
4677
4678 /* Decode file format */
4679 if (inserted > 0)
4680 {
4681 int empty_undo_list_p = 0;
4682
4683 /* If we're anyway going to discard undo information, don't
4684 record it in the first place. The buffer's undo list at this
4685 point is either nil or t when visiting a file. */
4686 if (!NILP (visit))
4687 {
4688 empty_undo_list_p = NILP (current_buffer->undo_list);
4689 current_buffer->undo_list = Qt;
4690 }
4691
4692 insval = call3 (Qformat_decode,
4693 Qnil, make_number (inserted), visit);
4694 CHECK_NUMBER (insval);
4695 inserted = XFASTINT (insval);
4696
4697 if (!NILP (visit))
4698 current_buffer->undo_list = empty_undo_list_p ? Qnil : Qt;
4699 }
4700
4701 /* Call after-change hooks for the inserted text, aside from the case
4702 of normal visiting (not with REPLACE), which is done in a new buffer
4703 "before" the buffer is changed. */
4704 if (inserted > 0 && total > 0
4705 && (NILP (visit) || !NILP (replace)))
4706 {
4707 signal_after_change (PT, 0, inserted);
4708 update_compositions (PT, PT, CHECK_BORDER);
4709 }
4710
4711 p = Vafter_insert_file_functions;
4712 while (CONSP (p))
4713 {
4714 insval = call1 (XCAR (p), make_number (inserted));
4715 if (!NILP (insval))
4716 {
4717 CHECK_NUMBER (insval);
4718 inserted = XFASTINT (insval);
4719 }
4720 QUIT;
4721 p = XCDR (p);
4722 }
4723
4724 if (!NILP (visit)
4725 && current_buffer->modtime == -1)
4726 {
4727 /* If visiting nonexistent file, return nil. */
4728 report_file_error ("Opening input file", Fcons (orig_filename, Qnil));
4729 }
4730
4731 if (read_quit)
4732 Fsignal (Qquit, Qnil);
4733
4734 /* ??? Retval needs to be dealt with in all cases consistently. */
4735 if (NILP (val))
4736 val = Fcons (orig_filename,
4737 Fcons (make_number (inserted),
4738 Qnil));
4739
4740 RETURN_UNGCPRO (unbind_to (count, val));
4741 }
4742 \f
4743 static Lisp_Object build_annotations P_ ((Lisp_Object, Lisp_Object));
4744 static Lisp_Object build_annotations_2 P_ ((Lisp_Object, Lisp_Object,
4745 Lisp_Object, Lisp_Object));
4746
4747 /* If build_annotations switched buffers, switch back to BUF.
4748 Kill the temporary buffer that was selected in the meantime.
4749
4750 Since this kill only the last temporary buffer, some buffers remain
4751 not killed if build_annotations switched buffers more than once.
4752 -- K.Handa */
4753
4754 static Lisp_Object
4755 build_annotations_unwind (buf)
4756 Lisp_Object buf;
4757 {
4758 Lisp_Object tembuf;
4759
4760 if (XBUFFER (buf) == current_buffer)
4761 return Qnil;
4762 tembuf = Fcurrent_buffer ();
4763 Fset_buffer (buf);
4764 Fkill_buffer (tembuf);
4765 return Qnil;
4766 }
4767
4768 /* Decide the coding-system to encode the data with. */
4769
4770 void
4771 choose_write_coding_system (start, end, filename,
4772 append, visit, lockname, coding)
4773 Lisp_Object start, end, filename, append, visit, lockname;
4774 struct coding_system *coding;
4775 {
4776 Lisp_Object val;
4777
4778 if (auto_saving
4779 && NILP (Fstring_equal (current_buffer->filename,
4780 current_buffer->auto_save_file_name)))
4781 {
4782 /* We use emacs-mule for auto saving... */
4783 setup_coding_system (Qemacs_mule, coding);
4784 /* ... but with the special flag to indicate not to strip off
4785 leading code of eight-bit-control chars. */
4786 coding->flags = 1;
4787 goto done_setup_coding;
4788 }
4789 else if (!NILP (Vcoding_system_for_write))
4790 {
4791 val = Vcoding_system_for_write;
4792 if (coding_system_require_warning
4793 && !NILP (Ffboundp (Vselect_safe_coding_system_function)))
4794 /* Confirm that VAL can surely encode the current region. */
4795 val = call5 (Vselect_safe_coding_system_function,
4796 start, end, Fcons (Qt, Fcons (val, Qnil)),
4797 Qnil, filename);
4798 }
4799 else
4800 {
4801 /* If the variable `buffer-file-coding-system' is set locally,
4802 it means that the file was read with some kind of code
4803 conversion or the variable is explicitly set by users. We
4804 had better write it out with the same coding system even if
4805 `enable-multibyte-characters' is nil.
4806
4807 If it is not set locally, we anyway have to convert EOL
4808 format if the default value of `buffer-file-coding-system'
4809 tells that it is not Unix-like (LF only) format. */
4810 int using_default_coding = 0;
4811 int force_raw_text = 0;
4812
4813 val = current_buffer->buffer_file_coding_system;
4814 if (NILP (val)
4815 || NILP (Flocal_variable_p (Qbuffer_file_coding_system, Qnil)))
4816 {
4817 val = Qnil;
4818 if (NILP (current_buffer->enable_multibyte_characters))
4819 force_raw_text = 1;
4820 }
4821
4822 if (NILP (val))
4823 {
4824 /* Check file-coding-system-alist. */
4825 Lisp_Object args[7], coding_systems;
4826
4827 args[0] = Qwrite_region; args[1] = start; args[2] = end;
4828 args[3] = filename; args[4] = append; args[5] = visit;
4829 args[6] = lockname;
4830 coding_systems = Ffind_operation_coding_system (7, args);
4831 if (CONSP (coding_systems) && !NILP (XCDR (coding_systems)))
4832 val = XCDR (coding_systems);
4833 }
4834
4835 if (NILP (val)
4836 && !NILP (current_buffer->buffer_file_coding_system))
4837 {
4838 /* If we still have not decided a coding system, use the
4839 default value of buffer-file-coding-system. */
4840 val = current_buffer->buffer_file_coding_system;
4841 using_default_coding = 1;
4842 }
4843
4844 if (!force_raw_text
4845 && !NILP (Ffboundp (Vselect_safe_coding_system_function)))
4846 /* Confirm that VAL can surely encode the current region. */
4847 val = call5 (Vselect_safe_coding_system_function,
4848 start, end, val, Qnil, filename);
4849
4850 setup_coding_system (Fcheck_coding_system (val), coding);
4851 if (coding->eol_type == CODING_EOL_UNDECIDED
4852 && !using_default_coding)
4853 {
4854 if (! EQ (default_buffer_file_coding.symbol,
4855 buffer_defaults.buffer_file_coding_system))
4856 setup_coding_system (buffer_defaults.buffer_file_coding_system,
4857 &default_buffer_file_coding);
4858 if (default_buffer_file_coding.eol_type != CODING_EOL_UNDECIDED)
4859 {
4860 Lisp_Object subsidiaries;
4861
4862 coding->eol_type = default_buffer_file_coding.eol_type;
4863 subsidiaries = Fget (coding->symbol, Qeol_type);
4864 if (VECTORP (subsidiaries)
4865 && XVECTOR (subsidiaries)->size == 3)
4866 coding->symbol
4867 = XVECTOR (subsidiaries)->contents[coding->eol_type];
4868 }
4869 }
4870
4871 if (force_raw_text)
4872 setup_raw_text_coding_system (coding);
4873 goto done_setup_coding;
4874 }
4875
4876 setup_coding_system (Fcheck_coding_system (val), coding);
4877
4878 done_setup_coding:
4879 if (!STRINGP (start) && !NILP (current_buffer->selective_display))
4880 coding->mode |= CODING_MODE_SELECTIVE_DISPLAY;
4881 }
4882
4883 DEFUN ("write-region", Fwrite_region, Swrite_region, 3, 7,
4884 "r\nFWrite region to file: \ni\ni\ni\np",
4885 doc: /* Write current region into specified file.
4886 When called from a program, requires three arguments:
4887 START, END and FILENAME. START and END are normally buffer positions
4888 specifying the part of the buffer to write.
4889 If START is nil, that means to use the entire buffer contents.
4890 If START is a string, then output that string to the file
4891 instead of any buffer contents; END is ignored.
4892
4893 Optional fourth argument APPEND if non-nil means
4894 append to existing file contents (if any). If it is an integer,
4895 seek to that offset in the file before writing.
4896 Optional fifth argument VISIT, if t or a string, means
4897 set the last-save-file-modtime of buffer to this file's modtime
4898 and mark buffer not modified.
4899 If VISIT is a string, it is a second file name;
4900 the output goes to FILENAME, but the buffer is marked as visiting VISIT.
4901 VISIT is also the file name to lock and unlock for clash detection.
4902 If VISIT is neither t nor nil nor a string,
4903 that means do not display the \"Wrote file\" message.
4904 The optional sixth arg LOCKNAME, if non-nil, specifies the name to
4905 use for locking and unlocking, overriding FILENAME and VISIT.
4906 The optional seventh arg MUSTBENEW, if non-nil, insists on a check
4907 for an existing file with the same name. If MUSTBENEW is `excl',
4908 that means to get an error if the file already exists; never overwrite.
4909 If MUSTBENEW is neither nil nor `excl', that means ask for
4910 confirmation before overwriting, but do go ahead and overwrite the file
4911 if the user confirms.
4912
4913 This does code conversion according to the value of
4914 `coding-system-for-write', `buffer-file-coding-system', or
4915 `file-coding-system-alist', and sets the variable
4916 `last-coding-system-used' to the coding system actually used. */)
4917 (start, end, filename, append, visit, lockname, mustbenew)
4918 Lisp_Object start, end, filename, append, visit, lockname, mustbenew;
4919 {
4920 register int desc;
4921 int failure;
4922 int save_errno = 0;
4923 const unsigned char *fn;
4924 struct stat st;
4925 int tem;
4926 int count = SPECPDL_INDEX ();
4927 int count1;
4928 #ifdef VMS
4929 unsigned char *fname = 0; /* If non-0, original filename (must rename) */
4930 #endif /* VMS */
4931 Lisp_Object handler;
4932 Lisp_Object visit_file;
4933 Lisp_Object annotations;
4934 Lisp_Object encoded_filename;
4935 int visiting = (EQ (visit, Qt) || STRINGP (visit));
4936 int quietly = !NILP (visit);
4937 struct gcpro gcpro1, gcpro2, gcpro3, gcpro4, gcpro5;
4938 struct buffer *given_buffer;
4939 #ifdef DOS_NT
4940 int buffer_file_type = O_BINARY;
4941 #endif /* DOS_NT */
4942 struct coding_system coding;
4943
4944 if (current_buffer->base_buffer && visiting)
4945 error ("Cannot do file visiting in an indirect buffer");
4946
4947 if (!NILP (start) && !STRINGP (start))
4948 validate_region (&start, &end);
4949
4950 GCPRO5 (start, filename, visit, visit_file, lockname);
4951
4952 filename = Fexpand_file_name (filename, Qnil);
4953
4954 if (!NILP (mustbenew) && !EQ (mustbenew, Qexcl))
4955 barf_or_query_if_file_exists (filename, "overwrite", 1, 0, 1);
4956
4957 if (STRINGP (visit))
4958 visit_file = Fexpand_file_name (visit, Qnil);
4959 else
4960 visit_file = filename;
4961
4962 if (NILP (lockname))
4963 lockname = visit_file;
4964
4965 annotations = Qnil;
4966
4967 /* If the file name has special constructs in it,
4968 call the corresponding file handler. */
4969 handler = Ffind_file_name_handler (filename, Qwrite_region);
4970 /* If FILENAME has no handler, see if VISIT has one. */
4971 if (NILP (handler) && STRINGP (visit))
4972 handler = Ffind_file_name_handler (visit, Qwrite_region);
4973
4974 if (!NILP (handler))
4975 {
4976 Lisp_Object val;
4977 val = call6 (handler, Qwrite_region, start, end,
4978 filename, append, visit);
4979
4980 if (visiting)
4981 {
4982 SAVE_MODIFF = MODIFF;
4983 XSETFASTINT (current_buffer->save_length, Z - BEG);
4984 current_buffer->filename = visit_file;
4985 }
4986 UNGCPRO;
4987 return val;
4988 }
4989
4990 record_unwind_protect (save_restriction_restore, save_restriction_save ());
4991
4992 /* Special kludge to simplify auto-saving. */
4993 if (NILP (start))
4994 {
4995 XSETFASTINT (start, BEG);
4996 XSETFASTINT (end, Z);
4997 Fwiden ();
4998 }
4999
5000 record_unwind_protect (build_annotations_unwind, Fcurrent_buffer ());
5001 count1 = SPECPDL_INDEX ();
5002
5003 given_buffer = current_buffer;
5004
5005 if (!STRINGP (start))
5006 {
5007 annotations = build_annotations (start, end);
5008
5009 if (current_buffer != given_buffer)
5010 {
5011 XSETFASTINT (start, BEGV);
5012 XSETFASTINT (end, ZV);
5013 }
5014 }
5015
5016 UNGCPRO;
5017
5018 GCPRO5 (start, filename, annotations, visit_file, lockname);
5019
5020 /* Decide the coding-system to encode the data with.
5021 We used to make this choice before calling build_annotations, but that
5022 leads to problems when a write-annotate-function takes care of
5023 unsavable chars (as was the case with X-Symbol). */
5024 choose_write_coding_system (start, end, filename,
5025 append, visit, lockname, &coding);
5026 Vlast_coding_system_used = coding.symbol;
5027
5028 given_buffer = current_buffer;
5029 if (! STRINGP (start))
5030 {
5031 annotations = build_annotations_2 (start, end,
5032 coding.pre_write_conversion, annotations);
5033 if (current_buffer != given_buffer)
5034 {
5035 XSETFASTINT (start, BEGV);
5036 XSETFASTINT (end, ZV);
5037 }
5038 }
5039
5040 #ifdef CLASH_DETECTION
5041 if (!auto_saving)
5042 {
5043 #if 0 /* This causes trouble for GNUS. */
5044 /* If we've locked this file for some other buffer,
5045 query before proceeding. */
5046 if (!visiting && EQ (Ffile_locked_p (lockname), Qt))
5047 call2 (intern ("ask-user-about-lock"), filename, Vuser_login_name);
5048 #endif
5049
5050 lock_file (lockname);
5051 }
5052 #endif /* CLASH_DETECTION */
5053
5054 encoded_filename = ENCODE_FILE (filename);
5055
5056 fn = SDATA (encoded_filename);
5057 desc = -1;
5058 if (!NILP (append))
5059 #ifdef DOS_NT
5060 desc = emacs_open (fn, O_WRONLY | buffer_file_type, 0);
5061 #else /* not DOS_NT */
5062 desc = emacs_open (fn, O_WRONLY, 0);
5063 #endif /* not DOS_NT */
5064
5065 if (desc < 0 && (NILP (append) || errno == ENOENT))
5066 #ifdef VMS
5067 if (auto_saving) /* Overwrite any previous version of autosave file */
5068 {
5069 vms_truncate (fn); /* if fn exists, truncate to zero length */
5070 desc = emacs_open (fn, O_RDWR, 0);
5071 if (desc < 0)
5072 desc = creat_copy_attrs (STRINGP (current_buffer->filename)
5073 ? SDATA (current_buffer->filename) : 0,
5074 fn);
5075 }
5076 else /* Write to temporary name and rename if no errors */
5077 {
5078 Lisp_Object temp_name;
5079 temp_name = Ffile_name_directory (filename);
5080
5081 if (!NILP (temp_name))
5082 {
5083 temp_name = Fmake_temp_name (concat2 (temp_name,
5084 build_string ("$$SAVE$$")));
5085 fname = SDATA (filename);
5086 fn = SDATA (temp_name);
5087 desc = creat_copy_attrs (fname, fn);
5088 if (desc < 0)
5089 {
5090 /* If we can't open the temporary file, try creating a new
5091 version of the original file. VMS "creat" creates a
5092 new version rather than truncating an existing file. */
5093 fn = fname;
5094 fname = 0;
5095 desc = creat (fn, 0666);
5096 #if 0 /* This can clobber an existing file and fail to replace it,
5097 if the user runs out of space. */
5098 if (desc < 0)
5099 {
5100 /* We can't make a new version;
5101 try to truncate and rewrite existing version if any. */
5102 vms_truncate (fn);
5103 desc = emacs_open (fn, O_RDWR, 0);
5104 }
5105 #endif
5106 }
5107 }
5108 else
5109 desc = creat (fn, 0666);
5110 }
5111 #else /* not VMS */
5112 #ifdef DOS_NT
5113 desc = emacs_open (fn,
5114 O_WRONLY | O_CREAT | buffer_file_type
5115 | (EQ (mustbenew, Qexcl) ? O_EXCL : O_TRUNC),
5116 S_IREAD | S_IWRITE);
5117 #else /* not DOS_NT */
5118 desc = emacs_open (fn, O_WRONLY | O_TRUNC | O_CREAT
5119 | (EQ (mustbenew, Qexcl) ? O_EXCL : 0),
5120 auto_saving ? auto_save_mode_bits : 0666);
5121 #endif /* not DOS_NT */
5122 #endif /* not VMS */
5123
5124 if (desc < 0)
5125 {
5126 #ifdef CLASH_DETECTION
5127 save_errno = errno;
5128 if (!auto_saving) unlock_file (lockname);
5129 errno = save_errno;
5130 #endif /* CLASH_DETECTION */
5131 UNGCPRO;
5132 report_file_error ("Opening output file", Fcons (filename, Qnil));
5133 }
5134
5135 record_unwind_protect (close_file_unwind, make_number (desc));
5136
5137 if (!NILP (append) && !NILP (Ffile_regular_p (filename)))
5138 {
5139 long ret;
5140
5141 if (NUMBERP (append))
5142 ret = lseek (desc, XINT (append), 1);
5143 else
5144 ret = lseek (desc, 0, 2);
5145 if (ret < 0)
5146 {
5147 #ifdef CLASH_DETECTION
5148 if (!auto_saving) unlock_file (lockname);
5149 #endif /* CLASH_DETECTION */
5150 UNGCPRO;
5151 report_file_error ("Lseek error", Fcons (filename, Qnil));
5152 }
5153 }
5154
5155 UNGCPRO;
5156
5157 #ifdef VMS
5158 /*
5159 * Kludge Warning: The VMS C RTL likes to insert carriage returns
5160 * if we do writes that don't end with a carriage return. Furthermore
5161 * it cannot handle writes of more then 16K. The modified
5162 * version of "sys_write" in SYSDEP.C (see comment there) copes with
5163 * this EXCEPT for the last record (iff it doesn't end with a carriage
5164 * return). This implies that if your buffer doesn't end with a carriage
5165 * return, you get one free... tough. However it also means that if
5166 * we make two calls to sys_write (a la the following code) you can
5167 * get one at the gap as well. The easiest way to fix this (honest)
5168 * is to move the gap to the next newline (or the end of the buffer).
5169 * Thus this change.
5170 *
5171 * Yech!
5172 */
5173 if (GPT > BEG && GPT_ADDR[-1] != '\n')
5174 move_gap (find_next_newline (GPT, 1));
5175 #else
5176 /* Whether VMS or not, we must move the gap to the next of newline
5177 when we must put designation sequences at beginning of line. */
5178 if (INTEGERP (start)
5179 && coding.type == coding_type_iso2022
5180 && coding.flags & CODING_FLAG_ISO_DESIGNATE_AT_BOL
5181 && GPT > BEG && GPT_ADDR[-1] != '\n')
5182 {
5183 int opoint = PT, opoint_byte = PT_BYTE;
5184 scan_newline (PT, PT_BYTE, ZV, ZV_BYTE, 1, 0);
5185 move_gap_both (PT, PT_BYTE);
5186 SET_PT_BOTH (opoint, opoint_byte);
5187 }
5188 #endif
5189
5190 failure = 0;
5191 immediate_quit = 1;
5192
5193 if (STRINGP (start))
5194 {
5195 failure = 0 > a_write (desc, start, 0, SCHARS (start),
5196 &annotations, &coding);
5197 save_errno = errno;
5198 }
5199 else if (XINT (start) != XINT (end))
5200 {
5201 tem = CHAR_TO_BYTE (XINT (start));
5202
5203 if (XINT (start) < GPT)
5204 {
5205 failure = 0 > a_write (desc, Qnil, XINT (start),
5206 min (GPT, XINT (end)) - XINT (start),
5207 &annotations, &coding);
5208 save_errno = errno;
5209 }
5210
5211 if (XINT (end) > GPT && !failure)
5212 {
5213 tem = max (XINT (start), GPT);
5214 failure = 0 > a_write (desc, Qnil, tem , XINT (end) - tem,
5215 &annotations, &coding);
5216 save_errno = errno;
5217 }
5218 }
5219 else
5220 {
5221 /* If file was empty, still need to write the annotations */
5222 coding.mode |= CODING_MODE_LAST_BLOCK;
5223 failure = 0 > a_write (desc, Qnil, XINT (end), 0, &annotations, &coding);
5224 save_errno = errno;
5225 }
5226
5227 if (CODING_REQUIRE_FLUSHING (&coding)
5228 && !(coding.mode & CODING_MODE_LAST_BLOCK)
5229 && ! failure)
5230 {
5231 /* We have to flush out a data. */
5232 coding.mode |= CODING_MODE_LAST_BLOCK;
5233 failure = 0 > e_write (desc, Qnil, 0, 0, &coding);
5234 save_errno = errno;
5235 }
5236
5237 immediate_quit = 0;
5238
5239 #ifdef HAVE_FSYNC
5240 /* Note fsync appears to change the modtime on BSD4.2 (both vax and sun).
5241 Disk full in NFS may be reported here. */
5242 /* mib says that closing the file will try to write as fast as NFS can do
5243 it, and that means the fsync here is not crucial for autosave files. */
5244 if (!auto_saving && fsync (desc) < 0)
5245 {
5246 /* If fsync fails with EINTR, don't treat that as serious. */
5247 if (errno != EINTR)
5248 failure = 1, save_errno = errno;
5249 }
5250 #endif
5251
5252 /* Spurious "file has changed on disk" warnings have been
5253 observed on Suns as well.
5254 It seems that `close' can change the modtime, under nfs.
5255
5256 (This has supposedly been fixed in Sunos 4,
5257 but who knows about all the other machines with NFS?) */
5258 #if 0
5259
5260 /* On VMS and APOLLO, must do the stat after the close
5261 since closing changes the modtime. */
5262 #ifndef VMS
5263 #ifndef APOLLO
5264 /* Recall that #if defined does not work on VMS. */
5265 #define FOO
5266 fstat (desc, &st);
5267 #endif
5268 #endif
5269 #endif
5270
5271 /* NFS can report a write failure now. */
5272 if (emacs_close (desc) < 0)
5273 failure = 1, save_errno = errno;
5274
5275 #ifdef VMS
5276 /* If we wrote to a temporary name and had no errors, rename to real name. */
5277 if (fname)
5278 {
5279 if (!failure)
5280 failure = (rename (fn, fname) != 0), save_errno = errno;
5281 fn = fname;
5282 }
5283 #endif /* VMS */
5284
5285 #ifndef FOO
5286 stat (fn, &st);
5287 #endif
5288 /* Discard the unwind protect for close_file_unwind. */
5289 specpdl_ptr = specpdl + count1;
5290 /* Restore the original current buffer. */
5291 visit_file = unbind_to (count, visit_file);
5292
5293 #ifdef CLASH_DETECTION
5294 if (!auto_saving)
5295 unlock_file (lockname);
5296 #endif /* CLASH_DETECTION */
5297
5298 /* Do this before reporting IO error
5299 to avoid a "file has changed on disk" warning on
5300 next attempt to save. */
5301 if (visiting)
5302 current_buffer->modtime = st.st_mtime;
5303
5304 if (failure)
5305 error ("IO error writing %s: %s", SDATA (filename),
5306 emacs_strerror (save_errno));
5307
5308 if (visiting)
5309 {
5310 SAVE_MODIFF = MODIFF;
5311 XSETFASTINT (current_buffer->save_length, Z - BEG);
5312 current_buffer->filename = visit_file;
5313 update_mode_lines++;
5314 }
5315 else if (quietly)
5316 {
5317 if (auto_saving
5318 && ! NILP (Fstring_equal (current_buffer->filename,
5319 current_buffer->auto_save_file_name)))
5320 SAVE_MODIFF = MODIFF;
5321
5322 return Qnil;
5323 }
5324
5325 if (!auto_saving)
5326 message_with_string ((INTEGERP (append)
5327 ? "Updated %s"
5328 : ! NILP (append)
5329 ? "Added to %s"
5330 : "Wrote %s"),
5331 visit_file, 1);
5332
5333 return Qnil;
5334 }
5335 \f
5336 Lisp_Object merge ();
5337
5338 DEFUN ("car-less-than-car", Fcar_less_than_car, Scar_less_than_car, 2, 2, 0,
5339 doc: /* Return t if (car A) is numerically less than (car B). */)
5340 (a, b)
5341 Lisp_Object a, b;
5342 {
5343 return Flss (Fcar (a), Fcar (b));
5344 }
5345
5346 /* Build the complete list of annotations appropriate for writing out
5347 the text between START and END, by calling all the functions in
5348 write-region-annotate-functions and merging the lists they return.
5349 If one of these functions switches to a different buffer, we assume
5350 that buffer contains altered text. Therefore, the caller must
5351 make sure to restore the current buffer in all cases,
5352 as save-excursion would do. */
5353
5354 static Lisp_Object
5355 build_annotations (start, end)
5356 Lisp_Object start, end;
5357 {
5358 Lisp_Object annotations;
5359 Lisp_Object p, res;
5360 struct gcpro gcpro1, gcpro2;
5361 Lisp_Object original_buffer;
5362 int i, used_global = 0;
5363
5364 XSETBUFFER (original_buffer, current_buffer);
5365
5366 annotations = Qnil;
5367 p = Vwrite_region_annotate_functions;
5368 GCPRO2 (annotations, p);
5369 while (CONSP (p))
5370 {
5371 struct buffer *given_buffer = current_buffer;
5372 if (EQ (Qt, XCAR (p)) && !used_global)
5373 { /* Use the global value of the hook. */
5374 Lisp_Object arg[2];
5375 used_global = 1;
5376 arg[0] = Fdefault_value (Qwrite_region_annotate_functions);
5377 arg[1] = XCDR (p);
5378 p = Fappend (2, arg);
5379 continue;
5380 }
5381 Vwrite_region_annotations_so_far = annotations;
5382 res = call2 (XCAR (p), start, end);
5383 /* If the function makes a different buffer current,
5384 assume that means this buffer contains altered text to be output.
5385 Reset START and END from the buffer bounds
5386 and discard all previous annotations because they should have
5387 been dealt with by this function. */
5388 if (current_buffer != given_buffer)
5389 {
5390 XSETFASTINT (start, BEGV);
5391 XSETFASTINT (end, ZV);
5392 annotations = Qnil;
5393 }
5394 Flength (res); /* Check basic validity of return value */
5395 annotations = merge (annotations, res, Qcar_less_than_car);
5396 p = XCDR (p);
5397 }
5398
5399 /* Now do the same for annotation functions implied by the file-format */
5400 if (auto_saving && (!EQ (current_buffer->auto_save_file_format, Qt)))
5401 p = current_buffer->auto_save_file_format;
5402 else
5403 p = current_buffer->file_format;
5404 for (i = 0; CONSP (p); p = XCDR (p), ++i)
5405 {
5406 struct buffer *given_buffer = current_buffer;
5407
5408 Vwrite_region_annotations_so_far = annotations;
5409
5410 /* Value is either a list of annotations or nil if the function
5411 has written annotations to a temporary buffer, which is now
5412 current. */
5413 res = call5 (Qformat_annotate_function, XCAR (p), start, end,
5414 original_buffer, make_number (i));
5415 if (current_buffer != given_buffer)
5416 {
5417 XSETFASTINT (start, BEGV);
5418 XSETFASTINT (end, ZV);
5419 annotations = Qnil;
5420 }
5421
5422 if (CONSP (res))
5423 annotations = merge (annotations, res, Qcar_less_than_car);
5424 }
5425
5426 UNGCPRO;
5427 return annotations;
5428 }
5429
5430 static Lisp_Object
5431 build_annotations_2 (start, end, pre_write_conversion, annotations)
5432 Lisp_Object start, end, pre_write_conversion, annotations;
5433 {
5434 struct gcpro gcpro1;
5435 Lisp_Object res;
5436
5437 GCPRO1 (annotations);
5438 /* At last, do the same for the function PRE_WRITE_CONVERSION
5439 implied by the current coding-system. */
5440 if (!NILP (pre_write_conversion))
5441 {
5442 struct buffer *given_buffer = current_buffer;
5443 Vwrite_region_annotations_so_far = annotations;
5444 res = call2 (pre_write_conversion, start, end);
5445 Flength (res);
5446 annotations = (current_buffer != given_buffer
5447 ? res
5448 : merge (annotations, res, Qcar_less_than_car));
5449 }
5450
5451 UNGCPRO;
5452 return annotations;
5453 }
5454 \f
5455 /* Write to descriptor DESC the NCHARS chars starting at POS of STRING.
5456 If STRING is nil, POS is the character position in the current buffer.
5457 Intersperse with them the annotations from *ANNOT
5458 which fall within the range of POS to POS + NCHARS,
5459 each at its appropriate position.
5460
5461 We modify *ANNOT by discarding elements as we use them up.
5462
5463 The return value is negative in case of system call failure. */
5464
5465 static int
5466 a_write (desc, string, pos, nchars, annot, coding)
5467 int desc;
5468 Lisp_Object string;
5469 register int nchars;
5470 int pos;
5471 Lisp_Object *annot;
5472 struct coding_system *coding;
5473 {
5474 Lisp_Object tem;
5475 int nextpos;
5476 int lastpos = pos + nchars;
5477
5478 while (NILP (*annot) || CONSP (*annot))
5479 {
5480 tem = Fcar_safe (Fcar (*annot));
5481 nextpos = pos - 1;
5482 if (INTEGERP (tem))
5483 nextpos = XFASTINT (tem);
5484
5485 /* If there are no more annotations in this range,
5486 output the rest of the range all at once. */
5487 if (! (nextpos >= pos && nextpos <= lastpos))
5488 return e_write (desc, string, pos, lastpos, coding);
5489
5490 /* Output buffer text up to the next annotation's position. */
5491 if (nextpos > pos)
5492 {
5493 if (0 > e_write (desc, string, pos, nextpos, coding))
5494 return -1;
5495 pos = nextpos;
5496 }
5497 /* Output the annotation. */
5498 tem = Fcdr (Fcar (*annot));
5499 if (STRINGP (tem))
5500 {
5501 if (0 > e_write (desc, tem, 0, SCHARS (tem), coding))
5502 return -1;
5503 }
5504 *annot = Fcdr (*annot);
5505 }
5506 return 0;
5507 }
5508
5509 #ifndef WRITE_BUF_SIZE
5510 #define WRITE_BUF_SIZE (16 * 1024)
5511 #endif
5512
5513 /* Write text in the range START and END into descriptor DESC,
5514 encoding them with coding system CODING. If STRING is nil, START
5515 and END are character positions of the current buffer, else they
5516 are indexes to the string STRING. */
5517
5518 static int
5519 e_write (desc, string, start, end, coding)
5520 int desc;
5521 Lisp_Object string;
5522 int start, end;
5523 struct coding_system *coding;
5524 {
5525 register char *addr;
5526 register int nbytes;
5527 char buf[WRITE_BUF_SIZE];
5528 int return_val = 0;
5529
5530 if (start >= end)
5531 coding->composing = COMPOSITION_DISABLED;
5532 if (coding->composing != COMPOSITION_DISABLED)
5533 coding_save_composition (coding, start, end, string);
5534
5535 if (STRINGP (string))
5536 {
5537 addr = SDATA (string);
5538 nbytes = SBYTES (string);
5539 coding->src_multibyte = STRING_MULTIBYTE (string);
5540 }
5541 else if (start < end)
5542 {
5543 /* It is assured that the gap is not in the range START and END-1. */
5544 addr = CHAR_POS_ADDR (start);
5545 nbytes = CHAR_TO_BYTE (end) - CHAR_TO_BYTE (start);
5546 coding->src_multibyte
5547 = !NILP (current_buffer->enable_multibyte_characters);
5548 }
5549 else
5550 {
5551 addr = "";
5552 nbytes = 0;
5553 coding->src_multibyte = 1;
5554 }
5555
5556 /* We used to have a code for handling selective display here. But,
5557 now it is handled within encode_coding. */
5558 while (1)
5559 {
5560 int result;
5561
5562 result = encode_coding (coding, addr, buf, nbytes, WRITE_BUF_SIZE);
5563 if (coding->produced > 0)
5564 {
5565 coding->produced -= emacs_write (desc, buf, coding->produced);
5566 if (coding->produced)
5567 {
5568 return_val = -1;
5569 break;
5570 }
5571 }
5572 nbytes -= coding->consumed;
5573 addr += coding->consumed;
5574 if (result == CODING_FINISH_INSUFFICIENT_SRC
5575 && nbytes > 0)
5576 {
5577 /* The source text ends by an incomplete multibyte form.
5578 There's no way other than write it out as is. */
5579 nbytes -= emacs_write (desc, addr, nbytes);
5580 if (nbytes)
5581 {
5582 return_val = -1;
5583 break;
5584 }
5585 }
5586 if (nbytes <= 0)
5587 break;
5588 start += coding->consumed_char;
5589 if (coding->cmp_data)
5590 coding_adjust_composition_offset (coding, start);
5591 }
5592
5593 if (coding->cmp_data)
5594 coding_free_composition_data (coding);
5595
5596 return return_val;
5597 }
5598 \f
5599 DEFUN ("verify-visited-file-modtime", Fverify_visited_file_modtime,
5600 Sverify_visited_file_modtime, 1, 1, 0,
5601 doc: /* Return t if last mod time of BUF's visited file matches what BUF records.
5602 This means that the file has not been changed since it was visited or saved.
5603 See Info node `(elisp)Modification Time' for more details. */)
5604 (buf)
5605 Lisp_Object buf;
5606 {
5607 struct buffer *b;
5608 struct stat st;
5609 Lisp_Object handler;
5610 Lisp_Object filename;
5611
5612 CHECK_BUFFER (buf);
5613 b = XBUFFER (buf);
5614
5615 if (!STRINGP (b->filename)) return Qt;
5616 if (b->modtime == 0) return Qt;
5617
5618 /* If the file name has special constructs in it,
5619 call the corresponding file handler. */
5620 handler = Ffind_file_name_handler (b->filename,
5621 Qverify_visited_file_modtime);
5622 if (!NILP (handler))
5623 return call2 (handler, Qverify_visited_file_modtime, buf);
5624
5625 filename = ENCODE_FILE (b->filename);
5626
5627 if (stat (SDATA (filename), &st) < 0)
5628 {
5629 /* If the file doesn't exist now and didn't exist before,
5630 we say that it isn't modified, provided the error is a tame one. */
5631 if (errno == ENOENT || errno == EACCES || errno == ENOTDIR)
5632 st.st_mtime = -1;
5633 else
5634 st.st_mtime = 0;
5635 }
5636 if (st.st_mtime == b->modtime
5637 /* If both are positive, accept them if they are off by one second. */
5638 || (st.st_mtime > 0 && b->modtime > 0
5639 && (st.st_mtime == b->modtime + 1
5640 || st.st_mtime == b->modtime - 1)))
5641 return Qt;
5642 return Qnil;
5643 }
5644
5645 DEFUN ("clear-visited-file-modtime", Fclear_visited_file_modtime,
5646 Sclear_visited_file_modtime, 0, 0, 0,
5647 doc: /* Clear out records of last mod time of visited file.
5648 Next attempt to save will certainly not complain of a discrepancy. */)
5649 ()
5650 {
5651 current_buffer->modtime = 0;
5652 return Qnil;
5653 }
5654
5655 DEFUN ("visited-file-modtime", Fvisited_file_modtime,
5656 Svisited_file_modtime, 0, 0, 0,
5657 doc: /* Return the current buffer's recorded visited file modification time.
5658 The value is a list of the form (HIGH LOW), like the time values
5659 that `file-attributes' returns. If the current buffer has no recorded
5660 file modification time, this function returns 0.
5661 See Info node `(elisp)Modification Time' for more details. */)
5662 ()
5663 {
5664 Lisp_Object tcons;
5665 tcons = long_to_cons ((unsigned long) current_buffer->modtime);
5666 if (CONSP (tcons))
5667 return list2 (XCAR (tcons), XCDR (tcons));
5668 return tcons;
5669 }
5670
5671 DEFUN ("set-visited-file-modtime", Fset_visited_file_modtime,
5672 Sset_visited_file_modtime, 0, 1, 0,
5673 doc: /* Update buffer's recorded modification time from the visited file's time.
5674 Useful if the buffer was not read from the file normally
5675 or if the file itself has been changed for some known benign reason.
5676 An argument specifies the modification time value to use
5677 \(instead of that of the visited file), in the form of a list
5678 \(HIGH . LOW) or (HIGH LOW). */)
5679 (time_list)
5680 Lisp_Object time_list;
5681 {
5682 if (!NILP (time_list))
5683 current_buffer->modtime = cons_to_long (time_list);
5684 else
5685 {
5686 register Lisp_Object filename;
5687 struct stat st;
5688 Lisp_Object handler;
5689
5690 filename = Fexpand_file_name (current_buffer->filename, Qnil);
5691
5692 /* If the file name has special constructs in it,
5693 call the corresponding file handler. */
5694 handler = Ffind_file_name_handler (filename, Qset_visited_file_modtime);
5695 if (!NILP (handler))
5696 /* The handler can find the file name the same way we did. */
5697 return call2 (handler, Qset_visited_file_modtime, Qnil);
5698
5699 filename = ENCODE_FILE (filename);
5700
5701 if (stat (SDATA (filename), &st) >= 0)
5702 current_buffer->modtime = st.st_mtime;
5703 }
5704
5705 return Qnil;
5706 }
5707 \f
5708 Lisp_Object
5709 auto_save_error (error)
5710 Lisp_Object error;
5711 {
5712 Lisp_Object args[3], msg;
5713 int i, nbytes;
5714 struct gcpro gcpro1;
5715
5716 ring_bell ();
5717
5718 args[0] = build_string ("Auto-saving %s: %s");
5719 args[1] = current_buffer->name;
5720 args[2] = Ferror_message_string (error);
5721 msg = Fformat (3, args);
5722 GCPRO1 (msg);
5723 nbytes = SBYTES (msg);
5724
5725 for (i = 0; i < 3; ++i)
5726 {
5727 if (i == 0)
5728 message2 (SDATA (msg), nbytes, STRING_MULTIBYTE (msg));
5729 else
5730 message2_nolog (SDATA (msg), nbytes, STRING_MULTIBYTE (msg));
5731 Fsleep_for (make_number (1), Qnil);
5732 }
5733
5734 UNGCPRO;
5735 return Qnil;
5736 }
5737
5738 Lisp_Object
5739 auto_save_1 ()
5740 {
5741 struct stat st;
5742 Lisp_Object modes;
5743
5744 auto_save_mode_bits = 0666;
5745
5746 /* Get visited file's mode to become the auto save file's mode. */
5747 if (! NILP (current_buffer->filename))
5748 {
5749 if (stat (SDATA (current_buffer->filename), &st) >= 0)
5750 /* But make sure we can overwrite it later! */
5751 auto_save_mode_bits = st.st_mode | 0600;
5752 else if ((modes = Ffile_modes (current_buffer->filename),
5753 INTEGERP (modes)))
5754 /* Remote files don't cooperate with stat. */
5755 auto_save_mode_bits = XINT (modes) | 0600;
5756 }
5757
5758 return
5759 Fwrite_region (Qnil, Qnil,
5760 current_buffer->auto_save_file_name,
5761 Qnil, Qlambda, Qnil, Qnil);
5762 }
5763
5764 static Lisp_Object
5765 do_auto_save_unwind (stream) /* used as unwind-protect function */
5766 Lisp_Object stream;
5767 {
5768 auto_saving = 0;
5769 if (!NILP (stream))
5770 fclose ((FILE *) (XFASTINT (XCAR (stream)) << 16
5771 | XFASTINT (XCDR (stream))));
5772 return Qnil;
5773 }
5774
5775 static Lisp_Object
5776 do_auto_save_unwind_1 (value) /* used as unwind-protect function */
5777 Lisp_Object value;
5778 {
5779 minibuffer_auto_raise = XINT (value);
5780 return Qnil;
5781 }
5782
5783 static Lisp_Object
5784 do_auto_save_make_dir (dir)
5785 Lisp_Object dir;
5786 {
5787 return call2 (Qmake_directory, dir, Qt);
5788 }
5789
5790 static Lisp_Object
5791 do_auto_save_eh (ignore)
5792 Lisp_Object ignore;
5793 {
5794 return Qnil;
5795 }
5796
5797 DEFUN ("do-auto-save", Fdo_auto_save, Sdo_auto_save, 0, 2, "",
5798 doc: /* Auto-save all buffers that need it.
5799 This is all buffers that have auto-saving enabled
5800 and are changed since last auto-saved.
5801 Auto-saving writes the buffer into a file
5802 so that your editing is not lost if the system crashes.
5803 This file is not the file you visited; that changes only when you save.
5804 Normally we run the normal hook `auto-save-hook' before saving.
5805
5806 A non-nil NO-MESSAGE argument means do not print any message if successful.
5807 A non-nil CURRENT-ONLY argument means save only current buffer. */)
5808 (no_message, current_only)
5809 Lisp_Object no_message, current_only;
5810 {
5811 struct buffer *old = current_buffer, *b;
5812 Lisp_Object tail, buf;
5813 int auto_saved = 0;
5814 int do_handled_files;
5815 Lisp_Object oquit;
5816 FILE *stream;
5817 Lisp_Object lispstream;
5818 int count = SPECPDL_INDEX ();
5819 int orig_minibuffer_auto_raise = minibuffer_auto_raise;
5820 int old_message_p = 0;
5821 struct gcpro gcpro1, gcpro2;
5822
5823 if (max_specpdl_size < specpdl_size + 40)
5824 max_specpdl_size = specpdl_size + 40;
5825
5826 if (minibuf_level)
5827 no_message = Qt;
5828
5829 if (NILP (no_message))
5830 {
5831 old_message_p = push_message ();
5832 record_unwind_protect (pop_message_unwind, Qnil);
5833 }
5834
5835 /* Ordinarily don't quit within this function,
5836 but don't make it impossible to quit (in case we get hung in I/O). */
5837 oquit = Vquit_flag;
5838 Vquit_flag = Qnil;
5839
5840 /* No GCPRO needed, because (when it matters) all Lisp_Object variables
5841 point to non-strings reached from Vbuffer_alist. */
5842
5843 if (!NILP (Vrun_hooks))
5844 call1 (Vrun_hooks, intern ("auto-save-hook"));
5845
5846 if (STRINGP (Vauto_save_list_file_name))
5847 {
5848 Lisp_Object listfile;
5849
5850 listfile = Fexpand_file_name (Vauto_save_list_file_name, Qnil);
5851
5852 /* Don't try to create the directory when shutting down Emacs,
5853 because creating the directory might signal an error, and
5854 that would leave Emacs in a strange state. */
5855 if (!NILP (Vrun_hooks))
5856 {
5857 Lisp_Object dir;
5858 dir = Qnil;
5859 GCPRO2 (dir, listfile);
5860 dir = Ffile_name_directory (listfile);
5861 if (NILP (Ffile_directory_p (dir)))
5862 internal_condition_case_1 (do_auto_save_make_dir,
5863 dir, Fcons (Fcons (Qfile_error, Qnil), Qnil),
5864 do_auto_save_eh);
5865 UNGCPRO;
5866 }
5867
5868 stream = fopen (SDATA (listfile), "w");
5869 if (stream != NULL)
5870 {
5871 /* Arrange to close that file whether or not we get an error.
5872 Also reset auto_saving to 0. */
5873 lispstream = Fcons (Qnil, Qnil);
5874 XSETCARFASTINT (lispstream, (EMACS_UINT)stream >> 16);
5875 XSETCDRFASTINT (lispstream, (EMACS_UINT)stream & 0xffff);
5876 }
5877 else
5878 lispstream = Qnil;
5879 }
5880 else
5881 {
5882 stream = NULL;
5883 lispstream = Qnil;
5884 }
5885
5886 record_unwind_protect (do_auto_save_unwind, lispstream);
5887 record_unwind_protect (do_auto_save_unwind_1,
5888 make_number (minibuffer_auto_raise));
5889 minibuffer_auto_raise = 0;
5890 auto_saving = 1;
5891
5892 /* On first pass, save all files that don't have handlers.
5893 On second pass, save all files that do have handlers.
5894
5895 If Emacs is crashing, the handlers may tweak what is causing
5896 Emacs to crash in the first place, and it would be a shame if
5897 Emacs failed to autosave perfectly ordinary files because it
5898 couldn't handle some ange-ftp'd file. */
5899
5900 for (do_handled_files = 0; do_handled_files < 2; do_handled_files++)
5901 for (tail = Vbuffer_alist; GC_CONSP (tail); tail = XCDR (tail))
5902 {
5903 buf = XCDR (XCAR (tail));
5904 b = XBUFFER (buf);
5905
5906 /* Record all the buffers that have auto save mode
5907 in the special file that lists them. For each of these buffers,
5908 Record visited name (if any) and auto save name. */
5909 if (STRINGP (b->auto_save_file_name)
5910 && stream != NULL && do_handled_files == 0)
5911 {
5912 if (!NILP (b->filename))
5913 {
5914 fwrite (SDATA (b->filename), 1,
5915 SBYTES (b->filename), stream);
5916 }
5917 putc ('\n', stream);
5918 fwrite (SDATA (b->auto_save_file_name), 1,
5919 SBYTES (b->auto_save_file_name), stream);
5920 putc ('\n', stream);
5921 }
5922
5923 if (!NILP (current_only)
5924 && b != current_buffer)
5925 continue;
5926
5927 /* Don't auto-save indirect buffers.
5928 The base buffer takes care of it. */
5929 if (b->base_buffer)
5930 continue;
5931
5932 /* Check for auto save enabled
5933 and file changed since last auto save
5934 and file changed since last real save. */
5935 if (STRINGP (b->auto_save_file_name)
5936 && BUF_SAVE_MODIFF (b) < BUF_MODIFF (b)
5937 && b->auto_save_modified < BUF_MODIFF (b)
5938 /* -1 means we've turned off autosaving for a while--see below. */
5939 && XINT (b->save_length) >= 0
5940 && (do_handled_files
5941 || NILP (Ffind_file_name_handler (b->auto_save_file_name,
5942 Qwrite_region))))
5943 {
5944 EMACS_TIME before_time, after_time;
5945
5946 EMACS_GET_TIME (before_time);
5947
5948 /* If we had a failure, don't try again for 20 minutes. */
5949 if (b->auto_save_failure_time >= 0
5950 && EMACS_SECS (before_time) - b->auto_save_failure_time < 1200)
5951 continue;
5952
5953 if ((XFASTINT (b->save_length) * 10
5954 > (BUF_Z (b) - BUF_BEG (b)) * 13)
5955 /* A short file is likely to change a large fraction;
5956 spare the user annoying messages. */
5957 && XFASTINT (b->save_length) > 5000
5958 /* These messages are frequent and annoying for `*mail*'. */
5959 && !EQ (b->filename, Qnil)
5960 && NILP (no_message))
5961 {
5962 /* It has shrunk too much; turn off auto-saving here. */
5963 minibuffer_auto_raise = orig_minibuffer_auto_raise;
5964 message_with_string ("Buffer %s has shrunk a lot; auto save disabled in that buffer until next real save",
5965 b->name, 1);
5966 minibuffer_auto_raise = 0;
5967 /* Turn off auto-saving until there's a real save,
5968 and prevent any more warnings. */
5969 XSETINT (b->save_length, -1);
5970 Fsleep_for (make_number (1), Qnil);
5971 continue;
5972 }
5973 set_buffer_internal (b);
5974 if (!auto_saved && NILP (no_message))
5975 message1 ("Auto-saving...");
5976 internal_condition_case (auto_save_1, Qt, auto_save_error);
5977 auto_saved++;
5978 b->auto_save_modified = BUF_MODIFF (b);
5979 XSETFASTINT (current_buffer->save_length, Z - BEG);
5980 set_buffer_internal (old);
5981
5982 EMACS_GET_TIME (after_time);
5983
5984 /* If auto-save took more than 60 seconds,
5985 assume it was an NFS failure that got a timeout. */
5986 if (EMACS_SECS (after_time) - EMACS_SECS (before_time) > 60)
5987 b->auto_save_failure_time = EMACS_SECS (after_time);
5988 }
5989 }
5990
5991 /* Prevent another auto save till enough input events come in. */
5992 record_auto_save ();
5993
5994 if (auto_saved && NILP (no_message))
5995 {
5996 if (old_message_p)
5997 {
5998 /* If we are going to restore an old message,
5999 give time to read ours. */
6000 sit_for (1, 0, 0, 0, 0);
6001 restore_message ();
6002 }
6003 else
6004 /* If we displayed a message and then restored a state
6005 with no message, leave a "done" message on the screen. */
6006 message1 ("Auto-saving...done");
6007 }
6008
6009 Vquit_flag = oquit;
6010
6011 /* This restores the message-stack status. */
6012 unbind_to (count, Qnil);
6013 return Qnil;
6014 }
6015
6016 DEFUN ("set-buffer-auto-saved", Fset_buffer_auto_saved,
6017 Sset_buffer_auto_saved, 0, 0, 0,
6018 doc: /* Mark current buffer as auto-saved with its current text.
6019 No auto-save file will be written until the buffer changes again. */)
6020 ()
6021 {
6022 current_buffer->auto_save_modified = MODIFF;
6023 XSETFASTINT (current_buffer->save_length, Z - BEG);
6024 current_buffer->auto_save_failure_time = -1;
6025 return Qnil;
6026 }
6027
6028 DEFUN ("clear-buffer-auto-save-failure", Fclear_buffer_auto_save_failure,
6029 Sclear_buffer_auto_save_failure, 0, 0, 0,
6030 doc: /* Clear any record of a recent auto-save failure in the current buffer. */)
6031 ()
6032 {
6033 current_buffer->auto_save_failure_time = -1;
6034 return Qnil;
6035 }
6036
6037 DEFUN ("recent-auto-save-p", Frecent_auto_save_p, Srecent_auto_save_p,
6038 0, 0, 0,
6039 doc: /* Return t if buffer has been auto-saved since last read in or saved. */)
6040 ()
6041 {
6042 return (SAVE_MODIFF < current_buffer->auto_save_modified) ? Qt : Qnil;
6043 }
6044 \f
6045 /* Reading and completing file names */
6046 extern Lisp_Object Ffile_name_completion (), Ffile_name_all_completions ();
6047
6048 /* In the string VAL, change each $ to $$ and return the result. */
6049
6050 static Lisp_Object
6051 double_dollars (val)
6052 Lisp_Object val;
6053 {
6054 register const unsigned char *old;
6055 register unsigned char *new;
6056 register int n;
6057 int osize, count;
6058
6059 osize = SBYTES (val);
6060
6061 /* Count the number of $ characters. */
6062 for (n = osize, count = 0, old = SDATA (val); n > 0; n--)
6063 if (*old++ == '$') count++;
6064 if (count > 0)
6065 {
6066 old = SDATA (val);
6067 val = make_uninit_multibyte_string (SCHARS (val) + count,
6068 osize + count);
6069 new = SDATA (val);
6070 for (n = osize; n > 0; n--)
6071 if (*old != '$')
6072 *new++ = *old++;
6073 else
6074 {
6075 *new++ = '$';
6076 *new++ = '$';
6077 old++;
6078 }
6079 }
6080 return val;
6081 }
6082
6083 static Lisp_Object
6084 read_file_name_cleanup (arg)
6085 Lisp_Object arg;
6086 {
6087 return (current_buffer->directory = arg);
6088 }
6089
6090 DEFUN ("read-file-name-internal", Fread_file_name_internal, Sread_file_name_internal,
6091 3, 3, 0,
6092 doc: /* Internal subroutine for read-file-name. Do not call this. */)
6093 (string, dir, action)
6094 Lisp_Object string, dir, action;
6095 /* action is nil for complete, t for return list of completions,
6096 lambda for verify final value */
6097 {
6098 Lisp_Object name, specdir, realdir, val, orig_string;
6099 int changed;
6100 struct gcpro gcpro1, gcpro2, gcpro3, gcpro4, gcpro5;
6101
6102 CHECK_STRING (string);
6103
6104 realdir = dir;
6105 name = string;
6106 orig_string = Qnil;
6107 specdir = Qnil;
6108 changed = 0;
6109 /* No need to protect ACTION--we only compare it with t and nil. */
6110 GCPRO5 (string, realdir, name, specdir, orig_string);
6111
6112 if (SCHARS (string) == 0)
6113 {
6114 if (EQ (action, Qlambda))
6115 {
6116 UNGCPRO;
6117 return Qnil;
6118 }
6119 }
6120 else
6121 {
6122 orig_string = string;
6123 string = Fsubstitute_in_file_name (string);
6124 changed = NILP (Fstring_equal (string, orig_string));
6125 name = Ffile_name_nondirectory (string);
6126 val = Ffile_name_directory (string);
6127 if (! NILP (val))
6128 realdir = Fexpand_file_name (val, realdir);
6129 }
6130
6131 if (NILP (action))
6132 {
6133 specdir = Ffile_name_directory (string);
6134 val = Ffile_name_completion (name, realdir);
6135 UNGCPRO;
6136 if (!STRINGP (val))
6137 {
6138 if (changed)
6139 return double_dollars (string);
6140 return val;
6141 }
6142
6143 if (!NILP (specdir))
6144 val = concat2 (specdir, val);
6145 #ifndef VMS
6146 return double_dollars (val);
6147 #else /* not VMS */
6148 return val;
6149 #endif /* not VMS */
6150 }
6151 UNGCPRO;
6152
6153 if (EQ (action, Qt))
6154 {
6155 Lisp_Object all = Ffile_name_all_completions (name, realdir);
6156 Lisp_Object comp;
6157 int count;
6158
6159 if (NILP (Vread_file_name_predicate)
6160 || EQ (Vread_file_name_predicate, Qfile_exists_p))
6161 return all;
6162
6163 #ifndef VMS
6164 if (EQ (Vread_file_name_predicate, Qfile_directory_p))
6165 {
6166 /* Brute-force speed up for directory checking:
6167 Discard strings which don't end in a slash. */
6168 for (comp = Qnil; CONSP (all); all = XCDR (all))
6169 {
6170 Lisp_Object tem = XCAR (all);
6171 int len;
6172 if (STRINGP (tem) &&
6173 (len = SCHARS (tem), len > 0) &&
6174 IS_DIRECTORY_SEP (SREF (tem, len-1)))
6175 comp = Fcons (tem, comp);
6176 }
6177 }
6178 else
6179 #endif
6180 {
6181 /* Must do it the hard (and slow) way. */
6182 GCPRO3 (all, comp, specdir);
6183 count = SPECPDL_INDEX ();
6184 record_unwind_protect (read_file_name_cleanup, current_buffer->directory);
6185 current_buffer->directory = realdir;
6186 for (comp = Qnil; CONSP (all); all = XCDR (all))
6187 if (!NILP (call1 (Vread_file_name_predicate, XCAR (all))))
6188 comp = Fcons (XCAR (all), comp);
6189 unbind_to (count, Qnil);
6190 UNGCPRO;
6191 }
6192 return Fnreverse (comp);
6193 }
6194
6195 /* Only other case actually used is ACTION = lambda */
6196 #ifdef VMS
6197 /* Supposedly this helps commands such as `cd' that read directory names,
6198 but can someone explain how it helps them? -- RMS */
6199 if (SCHARS (name) == 0)
6200 return Qt;
6201 #endif /* VMS */
6202 string = Fexpand_file_name (string, dir);
6203 if (!NILP (Vread_file_name_predicate))
6204 return call1 (Vread_file_name_predicate, string);
6205 return Ffile_exists_p (string);
6206 }
6207
6208 DEFUN ("next-read-file-uses-dialog-p", Fnext_read_file_uses_dialog_p,
6209 Snext_read_file_uses_dialog_p, 0, 0, 0,
6210 doc: /* Return t if a call to `read-file-name' will use a dialog.
6211 The return value is only relevant for a call to `read-file-name' that happens
6212 before any other event (mouse or keypress) is handeled. */)
6213 ()
6214 {
6215 #if defined (USE_MOTIF) || defined (HAVE_NTGUI) || defined (USE_GTK) || defined (HAVE_CARBON)
6216 if ((NILP (last_nonmenu_event) || CONSP (last_nonmenu_event))
6217 && use_dialog_box
6218 && use_file_dialog
6219 && have_menus_p ())
6220 return Qt;
6221 #endif
6222 return Qnil;
6223 }
6224
6225 DEFUN ("read-file-name", Fread_file_name, Sread_file_name, 1, 6, 0,
6226 doc: /* Read file name, prompting with PROMPT and completing in directory DIR.
6227 Value is not expanded---you must call `expand-file-name' yourself.
6228 Default name to DEFAULT-FILENAME if user exits the minibuffer with
6229 the same non-empty string that was inserted by this function.
6230 (If DEFAULT-FILENAME is omitted, the visited file name is used,
6231 except that if INITIAL is specified, that combined with DIR is used.)
6232 If the user exits with an empty minibuffer, this function returns
6233 an empty string. (This can only happen if the user erased the
6234 pre-inserted contents or if `insert-default-directory' is nil.)
6235 Fourth arg MUSTMATCH non-nil means require existing file's name.
6236 Non-nil and non-t means also require confirmation after completion.
6237 Fifth arg INITIAL specifies text to start with.
6238 If optional sixth arg PREDICATE is non-nil, possible completions and
6239 the resulting file name must satisfy (funcall PREDICATE NAME).
6240 DIR should be an absolute directory name. It defaults to the value of
6241 `default-directory'.
6242
6243 If this command was invoked with the mouse, use a file dialog box if
6244 `use-dialog-box' is non-nil, and the window system or X toolkit in use
6245 provides a file dialog box.
6246
6247 See also `read-file-name-completion-ignore-case'
6248 and `read-file-name-function'. */)
6249 (prompt, dir, default_filename, mustmatch, initial, predicate)
6250 Lisp_Object prompt, dir, default_filename, mustmatch, initial, predicate;
6251 {
6252 Lisp_Object val, insdef, tem;
6253 struct gcpro gcpro1, gcpro2;
6254 register char *homedir;
6255 Lisp_Object decoded_homedir;
6256 int replace_in_history = 0;
6257 int add_to_history = 0;
6258 int count;
6259
6260 if (NILP (dir))
6261 dir = current_buffer->directory;
6262 if (NILP (Ffile_name_absolute_p (dir)))
6263 dir = Fexpand_file_name (dir, Qnil);
6264 if (NILP (default_filename))
6265 default_filename
6266 = (!NILP (initial)
6267 ? Fexpand_file_name (initial, dir)
6268 : current_buffer->filename);
6269
6270 /* If dir starts with user's homedir, change that to ~. */
6271 homedir = (char *) egetenv ("HOME");
6272 #ifdef DOS_NT
6273 /* homedir can be NULL in temacs, since Vprocess_environment is not
6274 yet set up. We shouldn't crash in that case. */
6275 if (homedir != 0)
6276 {
6277 homedir = strcpy (alloca (strlen (homedir) + 1), homedir);
6278 CORRECT_DIR_SEPS (homedir);
6279 }
6280 #endif
6281 if (homedir != 0)
6282 decoded_homedir
6283 = DECODE_FILE (make_unibyte_string (homedir, strlen (homedir)));
6284 if (homedir != 0
6285 && STRINGP (dir)
6286 && !strncmp (SDATA (decoded_homedir), SDATA (dir),
6287 SBYTES (decoded_homedir))
6288 && IS_DIRECTORY_SEP (SREF (dir, SBYTES (decoded_homedir))))
6289 {
6290 dir = Fsubstring (dir, make_number (SCHARS (decoded_homedir)), Qnil);
6291 dir = concat2 (build_string ("~"), dir);
6292 }
6293 /* Likewise for default_filename. */
6294 if (homedir != 0
6295 && STRINGP (default_filename)
6296 && !strncmp (SDATA (decoded_homedir), SDATA (default_filename),
6297 SBYTES (decoded_homedir))
6298 && IS_DIRECTORY_SEP (SREF (default_filename, SBYTES (decoded_homedir))))
6299 {
6300 default_filename
6301 = Fsubstring (default_filename,
6302 make_number (SCHARS (decoded_homedir)), Qnil);
6303 default_filename = concat2 (build_string ("~"), default_filename);
6304 }
6305 if (!NILP (default_filename))
6306 {
6307 CHECK_STRING (default_filename);
6308 default_filename = double_dollars (default_filename);
6309 }
6310
6311 if (insert_default_directory && STRINGP (dir))
6312 {
6313 insdef = dir;
6314 if (!NILP (initial))
6315 {
6316 Lisp_Object args[2], pos;
6317
6318 args[0] = insdef;
6319 args[1] = initial;
6320 insdef = Fconcat (2, args);
6321 pos = make_number (SCHARS (double_dollars (dir)));
6322 insdef = Fcons (double_dollars (insdef), pos);
6323 }
6324 else
6325 insdef = double_dollars (insdef);
6326 }
6327 else if (STRINGP (initial))
6328 insdef = Fcons (double_dollars (initial), make_number (0));
6329 else
6330 insdef = Qnil;
6331
6332 if (!NILP (Vread_file_name_function))
6333 {
6334 Lisp_Object args[7];
6335
6336 GCPRO2 (insdef, default_filename);
6337 args[0] = Vread_file_name_function;
6338 args[1] = prompt;
6339 args[2] = dir;
6340 args[3] = default_filename;
6341 args[4] = mustmatch;
6342 args[5] = initial;
6343 args[6] = predicate;
6344 RETURN_UNGCPRO (Ffuncall (7, args));
6345 }
6346
6347 count = SPECPDL_INDEX ();
6348 specbind (intern ("completion-ignore-case"),
6349 read_file_name_completion_ignore_case ? Qt : Qnil);
6350 specbind (intern ("minibuffer-completing-file-name"), Qt);
6351 specbind (intern ("read-file-name-predicate"),
6352 (NILP (predicate) ? Qfile_exists_p : predicate));
6353
6354 GCPRO2 (insdef, default_filename);
6355
6356 #if defined (USE_MOTIF) || defined (HAVE_NTGUI) || defined (USE_GTK) || defined (HAVE_CARBON)
6357 if (! NILP (Fnext_read_file_uses_dialog_p ()))
6358 {
6359 /* If DIR contains a file name, split it. */
6360 Lisp_Object file;
6361 file = Ffile_name_nondirectory (dir);
6362 if (SCHARS (file) && NILP (default_filename))
6363 {
6364 default_filename = file;
6365 dir = Ffile_name_directory (dir);
6366 }
6367 if (!NILP(default_filename))
6368 default_filename = Fexpand_file_name (default_filename, dir);
6369 val = Fx_file_dialog (prompt, dir, default_filename, mustmatch,
6370 EQ (predicate, Qfile_directory_p) ? Qt : Qnil);
6371 add_to_history = 1;
6372 }
6373 else
6374 #endif
6375 val = Fcompleting_read (prompt, intern ("read-file-name-internal"),
6376 dir, mustmatch, insdef,
6377 Qfile_name_history, default_filename, Qnil);
6378
6379 tem = Fsymbol_value (Qfile_name_history);
6380 if (CONSP (tem) && EQ (XCAR (tem), val))
6381 replace_in_history = 1;
6382
6383 /* If Fcompleting_read returned the inserted default string itself
6384 (rather than a new string with the same contents),
6385 it has to mean that the user typed RET with the minibuffer empty.
6386 In that case, we really want to return ""
6387 so that commands such as set-visited-file-name can distinguish. */
6388 if (EQ (val, default_filename))
6389 {
6390 /* In this case, Fcompleting_read has not added an element
6391 to the history. Maybe we should. */
6392 if (! replace_in_history)
6393 add_to_history = 1;
6394
6395 val = empty_string;
6396 }
6397
6398 unbind_to (count, Qnil);
6399 UNGCPRO;
6400 if (NILP (val))
6401 error ("No file name specified");
6402
6403 tem = Fstring_equal (val, CONSP (insdef) ? XCAR (insdef) : insdef);
6404
6405 if (!NILP (tem) && !NILP (default_filename))
6406 val = default_filename;
6407 val = Fsubstitute_in_file_name (val);
6408
6409 if (replace_in_history)
6410 /* Replace what Fcompleting_read added to the history
6411 with what we will actually return. */
6412 {
6413 Lisp_Object val1 = double_dollars (val);
6414 tem = Fsymbol_value (Qfile_name_history);
6415 if (history_delete_duplicates)
6416 XSETCDR (tem, Fdelete (val1, XCDR(tem)));
6417 XSETCAR (tem, val1);
6418 }
6419 else if (add_to_history)
6420 {
6421 /* Add the value to the history--but not if it matches
6422 the last value already there. */
6423 Lisp_Object val1 = double_dollars (val);
6424 tem = Fsymbol_value (Qfile_name_history);
6425 if (! CONSP (tem) || NILP (Fequal (XCAR (tem), val1)))
6426 {
6427 if (history_delete_duplicates) tem = Fdelete (val1, tem);
6428 Fset (Qfile_name_history, Fcons (val1, tem));
6429 }
6430 }
6431
6432 return val;
6433 }
6434
6435 \f
6436 void
6437 init_fileio_once ()
6438 {
6439 /* Must be set before any path manipulation is performed. */
6440 XSETFASTINT (Vdirectory_sep_char, '/');
6441 }
6442
6443 \f
6444 void
6445 syms_of_fileio ()
6446 {
6447 Qoperations = intern ("operations");
6448 Qexpand_file_name = intern ("expand-file-name");
6449 Qsubstitute_in_file_name = intern ("substitute-in-file-name");
6450 Qdirectory_file_name = intern ("directory-file-name");
6451 Qfile_name_directory = intern ("file-name-directory");
6452 Qfile_name_nondirectory = intern ("file-name-nondirectory");
6453 Qunhandled_file_name_directory = intern ("unhandled-file-name-directory");
6454 Qfile_name_as_directory = intern ("file-name-as-directory");
6455 Qcopy_file = intern ("copy-file");
6456 Qmake_directory_internal = intern ("make-directory-internal");
6457 Qmake_directory = intern ("make-directory");
6458 Qdelete_directory = intern ("delete-directory");
6459 Qdelete_file = intern ("delete-file");
6460 Qrename_file = intern ("rename-file");
6461 Qadd_name_to_file = intern ("add-name-to-file");
6462 Qmake_symbolic_link = intern ("make-symbolic-link");
6463 Qfile_exists_p = intern ("file-exists-p");
6464 Qfile_executable_p = intern ("file-executable-p");
6465 Qfile_readable_p = intern ("file-readable-p");
6466 Qfile_writable_p = intern ("file-writable-p");
6467 Qfile_symlink_p = intern ("file-symlink-p");
6468 Qaccess_file = intern ("access-file");
6469 Qfile_directory_p = intern ("file-directory-p");
6470 Qfile_regular_p = intern ("file-regular-p");
6471 Qfile_accessible_directory_p = intern ("file-accessible-directory-p");
6472 Qfile_modes = intern ("file-modes");
6473 Qset_file_modes = intern ("set-file-modes");
6474 Qset_file_times = intern ("set-file-times");
6475 Qfile_newer_than_file_p = intern ("file-newer-than-file-p");
6476 Qinsert_file_contents = intern ("insert-file-contents");
6477 Qwrite_region = intern ("write-region");
6478 Qverify_visited_file_modtime = intern ("verify-visited-file-modtime");
6479 Qset_visited_file_modtime = intern ("set-visited-file-modtime");
6480 Qauto_save_coding = intern ("auto-save-coding");
6481
6482 staticpro (&Qoperations);
6483 staticpro (&Qexpand_file_name);
6484 staticpro (&Qsubstitute_in_file_name);
6485 staticpro (&Qdirectory_file_name);
6486 staticpro (&Qfile_name_directory);
6487 staticpro (&Qfile_name_nondirectory);
6488 staticpro (&Qunhandled_file_name_directory);
6489 staticpro (&Qfile_name_as_directory);
6490 staticpro (&Qcopy_file);
6491 staticpro (&Qmake_directory_internal);
6492 staticpro (&Qmake_directory);
6493 staticpro (&Qdelete_directory);
6494 staticpro (&Qdelete_file);
6495 staticpro (&Qrename_file);
6496 staticpro (&Qadd_name_to_file);
6497 staticpro (&Qmake_symbolic_link);
6498 staticpro (&Qfile_exists_p);
6499 staticpro (&Qfile_executable_p);
6500 staticpro (&Qfile_readable_p);
6501 staticpro (&Qfile_writable_p);
6502 staticpro (&Qaccess_file);
6503 staticpro (&Qfile_symlink_p);
6504 staticpro (&Qfile_directory_p);
6505 staticpro (&Qfile_regular_p);
6506 staticpro (&Qfile_accessible_directory_p);
6507 staticpro (&Qfile_modes);
6508 staticpro (&Qset_file_modes);
6509 staticpro (&Qset_file_times);
6510 staticpro (&Qfile_newer_than_file_p);
6511 staticpro (&Qinsert_file_contents);
6512 staticpro (&Qwrite_region);
6513 staticpro (&Qverify_visited_file_modtime);
6514 staticpro (&Qset_visited_file_modtime);
6515 staticpro (&Qauto_save_coding);
6516
6517 Qfile_name_history = intern ("file-name-history");
6518 Fset (Qfile_name_history, Qnil);
6519 staticpro (&Qfile_name_history);
6520
6521 Qfile_error = intern ("file-error");
6522 staticpro (&Qfile_error);
6523 Qfile_already_exists = intern ("file-already-exists");
6524 staticpro (&Qfile_already_exists);
6525 Qfile_date_error = intern ("file-date-error");
6526 staticpro (&Qfile_date_error);
6527 Qexcl = intern ("excl");
6528 staticpro (&Qexcl);
6529
6530 #ifdef DOS_NT
6531 Qfind_buffer_file_type = intern ("find-buffer-file-type");
6532 staticpro (&Qfind_buffer_file_type);
6533 #endif /* DOS_NT */
6534
6535 DEFVAR_LISP ("file-name-coding-system", &Vfile_name_coding_system,
6536 doc: /* *Coding system for encoding file names.
6537 If it is nil, `default-file-name-coding-system' (which see) is used. */);
6538 Vfile_name_coding_system = Qnil;
6539
6540 DEFVAR_LISP ("default-file-name-coding-system",
6541 &Vdefault_file_name_coding_system,
6542 doc: /* Default coding system for encoding file names.
6543 This variable is used only when `file-name-coding-system' is nil.
6544
6545 This variable is set/changed by the command `set-language-environment'.
6546 User should not set this variable manually,
6547 instead use `file-name-coding-system' to get a constant encoding
6548 of file names regardless of the current language environment. */);
6549 Vdefault_file_name_coding_system = Qnil;
6550
6551 Qformat_decode = intern ("format-decode");
6552 staticpro (&Qformat_decode);
6553 Qformat_annotate_function = intern ("format-annotate-function");
6554 staticpro (&Qformat_annotate_function);
6555 Qafter_insert_file_set_coding = intern ("after-insert-file-set-coding");
6556 staticpro (&Qafter_insert_file_set_coding);
6557
6558 Qcar_less_than_car = intern ("car-less-than-car");
6559 staticpro (&Qcar_less_than_car);
6560
6561 Fput (Qfile_error, Qerror_conditions,
6562 Fcons (Qfile_error, Fcons (Qerror, Qnil)));
6563 Fput (Qfile_error, Qerror_message,
6564 build_string ("File error"));
6565
6566 Fput (Qfile_already_exists, Qerror_conditions,
6567 Fcons (Qfile_already_exists,
6568 Fcons (Qfile_error, Fcons (Qerror, Qnil))));
6569 Fput (Qfile_already_exists, Qerror_message,
6570 build_string ("File already exists"));
6571
6572 Fput (Qfile_date_error, Qerror_conditions,
6573 Fcons (Qfile_date_error,
6574 Fcons (Qfile_error, Fcons (Qerror, Qnil))));
6575 Fput (Qfile_date_error, Qerror_message,
6576 build_string ("Cannot set file date"));
6577
6578 DEFVAR_LISP ("read-file-name-function", &Vread_file_name_function,
6579 doc: /* If this is non-nil, `read-file-name' does its work by calling this function. */);
6580 Vread_file_name_function = Qnil;
6581
6582 DEFVAR_LISP ("read-file-name-predicate", &Vread_file_name_predicate,
6583 doc: /* Current predicate used by `read-file-name-internal'. */);
6584 Vread_file_name_predicate = Qnil;
6585
6586 DEFVAR_BOOL ("read-file-name-completion-ignore-case", &read_file_name_completion_ignore_case,
6587 doc: /* *Non-nil means when reading a file name completion ignores case. */);
6588 #if defined VMS || defined DOS_NT || defined MAC_OS
6589 read_file_name_completion_ignore_case = 1;
6590 #else
6591 read_file_name_completion_ignore_case = 0;
6592 #endif
6593
6594 DEFVAR_BOOL ("insert-default-directory", &insert_default_directory,
6595 doc: /* *Non-nil means when reading a filename start with default dir in minibuffer.
6596 If the initial minibuffer contents are non-empty, you can usually
6597 request a default filename by typing RETURN without editing. For some
6598 commands, exiting with an empty minibuffer has a special meaning,
6599 such as making the current buffer visit no file in the case of
6600 `set-visited-file-name'.
6601 If this variable is non-nil, the minibuffer contents are always
6602 initially non-empty and typing RETURN without editing will fetch the
6603 default name, if one is provided. Note however that this default name
6604 is not necessarily the name originally inserted in the minibuffer, if
6605 that is just the default directory.
6606 If this variable is nil, the minibuffer often starts out empty. In
6607 that case you may have to explicitly fetch the next history element to
6608 request the default name. */);
6609 insert_default_directory = 1;
6610
6611 DEFVAR_BOOL ("vms-stmlf-recfm", &vms_stmlf_recfm,
6612 doc: /* *Non-nil means write new files with record format `stmlf'.
6613 nil means use format `var'. This variable is meaningful only on VMS. */);
6614 vms_stmlf_recfm = 0;
6615
6616 DEFVAR_LISP ("directory-sep-char", &Vdirectory_sep_char,
6617 doc: /* Directory separator character for built-in functions that return file names.
6618 The value is always ?/. Don't use this variable, just use `/'. */);
6619
6620 DEFVAR_LISP ("file-name-handler-alist", &Vfile_name_handler_alist,
6621 doc: /* *Alist of elements (REGEXP . HANDLER) for file names handled specially.
6622 If a file name matches REGEXP, then all I/O on that file is done by calling
6623 HANDLER.
6624
6625 The first argument given to HANDLER is the name of the I/O primitive
6626 to be handled; the remaining arguments are the arguments that were
6627 passed to that primitive. For example, if you do
6628 (file-exists-p FILENAME)
6629 and FILENAME is handled by HANDLER, then HANDLER is called like this:
6630 (funcall HANDLER 'file-exists-p FILENAME)
6631 The function `find-file-name-handler' checks this list for a handler
6632 for its argument. */);
6633 Vfile_name_handler_alist = Qnil;
6634
6635 DEFVAR_LISP ("set-auto-coding-function",
6636 &Vset_auto_coding_function,
6637 doc: /* If non-nil, a function to call to decide a coding system of file.
6638 Two arguments are passed to this function: the file name
6639 and the length of a file contents following the point.
6640 This function should return a coding system to decode the file contents.
6641 It should check the file name against `auto-coding-alist'.
6642 If no coding system is decided, it should check a coding system
6643 specified in the heading lines with the format:
6644 -*- ... coding: CODING-SYSTEM; ... -*-
6645 or local variable spec of the tailing lines with `coding:' tag. */);
6646 Vset_auto_coding_function = Qnil;
6647
6648 DEFVAR_LISP ("after-insert-file-functions", &Vafter_insert_file_functions,
6649 doc: /* A list of functions to be called at the end of `insert-file-contents'.
6650 Each is passed one argument, the number of characters inserted.
6651 It should return the new character count, and leave point the same.
6652 If `insert-file-contents' is intercepted by a handler from
6653 `file-name-handler-alist', that handler is responsible for calling the
6654 functions in `after-insert-file-functions' if appropriate. */);
6655 Vafter_insert_file_functions = Qnil;
6656
6657 DEFVAR_LISP ("write-region-annotate-functions", &Vwrite_region_annotate_functions,
6658 doc: /* A list of functions to be called at the start of `write-region'.
6659 Each is passed two arguments, START and END as for `write-region'.
6660 These are usually two numbers but not always; see the documentation
6661 for `write-region'. The function should return a list of pairs
6662 of the form (POSITION . STRING), consisting of strings to be effectively
6663 inserted at the specified positions of the file being written (1 means to
6664 insert before the first byte written). The POSITIONs must be sorted into
6665 increasing order. If there are several functions in the list, the several
6666 lists are merged destructively. Alternatively, the function can return
6667 with a different buffer current; in that case it should pay attention
6668 to the annotations returned by previous functions and listed in
6669 `write-region-annotations-so-far'.*/);
6670 Vwrite_region_annotate_functions = Qnil;
6671 staticpro (&Qwrite_region_annotate_functions);
6672 Qwrite_region_annotate_functions
6673 = intern ("write-region-annotate-functions");
6674
6675 DEFVAR_LISP ("write-region-annotations-so-far",
6676 &Vwrite_region_annotations_so_far,
6677 doc: /* When an annotation function is called, this holds the previous annotations.
6678 These are the annotations made by other annotation functions
6679 that were already called. See also `write-region-annotate-functions'. */);
6680 Vwrite_region_annotations_so_far = Qnil;
6681
6682 DEFVAR_LISP ("inhibit-file-name-handlers", &Vinhibit_file_name_handlers,
6683 doc: /* A list of file name handlers that temporarily should not be used.
6684 This applies only to the operation `inhibit-file-name-operation'. */);
6685 Vinhibit_file_name_handlers = Qnil;
6686
6687 DEFVAR_LISP ("inhibit-file-name-operation", &Vinhibit_file_name_operation,
6688 doc: /* The operation for which `inhibit-file-name-handlers' is applicable. */);
6689 Vinhibit_file_name_operation = Qnil;
6690
6691 DEFVAR_LISP ("auto-save-list-file-name", &Vauto_save_list_file_name,
6692 doc: /* File name in which we write a list of all auto save file names.
6693 This variable is initialized automatically from `auto-save-list-file-prefix'
6694 shortly after Emacs reads your `.emacs' file, if you have not yet given it
6695 a non-nil value. */);
6696 Vauto_save_list_file_name = Qnil;
6697
6698 defsubr (&Sfind_file_name_handler);
6699 defsubr (&Sfile_name_directory);
6700 defsubr (&Sfile_name_nondirectory);
6701 defsubr (&Sunhandled_file_name_directory);
6702 defsubr (&Sfile_name_as_directory);
6703 defsubr (&Sdirectory_file_name);
6704 defsubr (&Smake_temp_name);
6705 defsubr (&Sexpand_file_name);
6706 defsubr (&Ssubstitute_in_file_name);
6707 defsubr (&Scopy_file);
6708 defsubr (&Smake_directory_internal);
6709 defsubr (&Sdelete_directory);
6710 defsubr (&Sdelete_file);
6711 defsubr (&Srename_file);
6712 defsubr (&Sadd_name_to_file);
6713 #ifdef S_IFLNK
6714 defsubr (&Smake_symbolic_link);
6715 #endif /* S_IFLNK */
6716 #ifdef VMS
6717 defsubr (&Sdefine_logical_name);
6718 #endif /* VMS */
6719 #ifdef HPUX_NET
6720 defsubr (&Ssysnetunam);
6721 #endif /* HPUX_NET */
6722 defsubr (&Sfile_name_absolute_p);
6723 defsubr (&Sfile_exists_p);
6724 defsubr (&Sfile_executable_p);
6725 defsubr (&Sfile_readable_p);
6726 defsubr (&Sfile_writable_p);
6727 defsubr (&Saccess_file);
6728 defsubr (&Sfile_symlink_p);
6729 defsubr (&Sfile_directory_p);
6730 defsubr (&Sfile_accessible_directory_p);
6731 defsubr (&Sfile_regular_p);
6732 defsubr (&Sfile_modes);
6733 defsubr (&Sset_file_modes);
6734 defsubr (&Sset_file_times);
6735 defsubr (&Sset_default_file_modes);
6736 defsubr (&Sdefault_file_modes);
6737 defsubr (&Sfile_newer_than_file_p);
6738 defsubr (&Sinsert_file_contents);
6739 defsubr (&Swrite_region);
6740 defsubr (&Scar_less_than_car);
6741 defsubr (&Sverify_visited_file_modtime);
6742 defsubr (&Sclear_visited_file_modtime);
6743 defsubr (&Svisited_file_modtime);
6744 defsubr (&Sset_visited_file_modtime);
6745 defsubr (&Sdo_auto_save);
6746 defsubr (&Sset_buffer_auto_saved);
6747 defsubr (&Sclear_buffer_auto_save_failure);
6748 defsubr (&Srecent_auto_save_p);
6749
6750 defsubr (&Sread_file_name_internal);
6751 defsubr (&Sread_file_name);
6752 defsubr (&Snext_read_file_uses_dialog_p);
6753
6754 #ifdef unix
6755 defsubr (&Sunix_sync);
6756 #endif
6757 }
6758
6759 /* arch-tag: 64ba3fd7-f844-4fb2-ba4b-427eb928786c
6760 (do not change this comment) */