/* File IO for GNU Emacs.
- Copyright (C) 1985, 1986, 1987, 1988, 1992, 1993 Free Software Foundation, Inc.
+ Copyright (C) 1985, 1986, 1987, 1988, 1993 Free Software Foundation, Inc.
This file is part of GNU Emacs.
#ifdef HPUX
#include <netio.h>
#ifndef HPUX8
+#ifndef HPUX9
#include <errnet.h>
#endif
#endif
+#endif
#ifndef O_WRONLY
#define O_WRONLY 1
Lisp_Object Qinsert_file_contents;
Lisp_Object Qwrite_region;
Lisp_Object Qverify_visited_file_modtime;
+Lisp_Object Qset_visited_file_modtime;
DEFUN ("find-file-name-handler", Ffind_file_name_handler, Sfind_file_name_handler, 1, 1, 0,
"Return FILENAME's handler function, if its syntax is handled specially.\n\
Lisp_Object handler;
struct gcpro gcpro1, gcpro2;
int count = specpdl_ptr - specpdl;
+ Lisp_Object args[6];
GCPRO2 (filename, newname);
CHECK_STRING (filename, 0);
/* If the input file name has special constructs in it,
call the corresponding file handler. */
handler = Ffind_file_name_handler (filename);
- if (!NILP (handler))
- return call3 (handler, Qcopy_file, filename, newname);
/* Likewise for output file name. */
- handler = Ffind_file_name_handler (newname);
+ if (NILP (handler))
+ handler = Ffind_file_name_handler (newname);
if (!NILP (handler))
- return call3 (handler, Qcopy_file, filename, newname);
+ return call5 (handler, Qcopy_file, filename, newname,
+ ok_if_already_exists, keep_date);
if (NILP (ok_if_already_exists)
|| XTYPE (ok_if_already_exists) == Lisp_Int)
/* If the file name has special constructs in it,
call the corresponding file handler. */
handler = Ffind_file_name_handler (filename);
+ if (NILP (handler))
+ handler = Ffind_file_name_handler (newname);
if (!NILP (handler))
- return call3 (handler, Qrename_file, filename, newname);
+ return call4 (handler, Qrename_file,
+ filename, newname, ok_if_already_exists);
if (NILP (ok_if_already_exists)
|| XTYPE (ok_if_already_exists) == Lisp_Int)
{
if (errno == EXDEV)
{
- Fcopy_file (filename, newname, ok_if_already_exists, Qt);
+ Fcopy_file (filename, newname,
+ /* We have already prompted if it was an integer,
+ so don't have copy-file prompt again. */
+ NILP (ok_if_already_exists) ? Qnil : Qt, Qt);
Fdelete_file (filename);
}
else
call the corresponding file handler. */
handler = Ffind_file_name_handler (filename);
if (!NILP (handler))
- return call3 (handler, Qadd_name_to_file, filename, newname);
+ return call4 (handler, Qadd_name_to_file, filename, newname,
+ ok_if_already_exists);
if (NILP (ok_if_already_exists)
|| XTYPE (ok_if_already_exists) == Lisp_Int)
call the corresponding file handler. */
handler = Ffind_file_name_handler (filename);
if (!NILP (handler))
- return call3 (handler, Qmake_symbolic_link, filename, linkname);
+ return call4 (handler, Qmake_symbolic_link, filename, linkname,
+ ok_if_already_exists);
if (NILP (ok_if_already_exists)
|| XTYPE (ok_if_already_exists) == Lisp_Int)
if (access (XSTRING (abspath)->data, 0) >= 0)
return ((access (XSTRING (abspath)->data, 2) >= 0
- && ! ro_fsys (XSTRING (abspath)))
+ && ! ro_fsys ((char *) XSTRING (abspath)->data))
? Qt : Qnil);
dir = Ffile_name_directory (abspath);
#ifdef VMS
dir = Fdirectory_file_name (dir);
#endif /* VMS */
return ((access (!NILP (dir) ? (char *) XSTRING (dir)->data : "", 2) >= 0
- && ! ro_fsys ((char *) XSTRING (dir)))
+ && ! ro_fsys ((char *) XSTRING (dir)->data))
? Qt : Qnil);
}
/* If the file name has special constructs in it,
call the corresponding file handler. */
handler = Ffind_file_name_handler (abspath1);
+ if (NILP (handler))
+ handler = Ffind_file_name_handler (abspath2);
if (!NILP (handler))
return call3 (handler, Qfile_newer_than_file_p, abspath1, abspath2);
}
\f
DEFUN ("insert-file-contents", Finsert_file_contents, Sinsert_file_contents,
- 1, 2, 0,
+ 1, 4, 0,
"Insert contents of file FILENAME after point.\n\
-Returns list of absolute pathname and length of data inserted.\n\
+Returns list of absolute file name and length of data inserted.\n\
If second argument VISIT is non-nil, the buffer's visited filename\n\
and last save file modtime are set, and it is marked unmodified.\n\
If visiting and the file does not exist, visiting is completed\n\
-before the error is signaled.")
- (filename, visit)
- Lisp_Object filename, visit;
+before the error is signaled.\n\n\
+The optional third and fourth arguments BEG and END\n\
+specify what portion of the file to insert.\n\
+If VISIT is non-nil, BEG and END must be nil.")
+ (filename, visit, beg, end)
+ Lisp_Object filename, visit, beg, end;
{
struct stat st;
register int fd;
int count = specpdl_ptr - specpdl;
struct gcpro gcpro1;
Lisp_Object handler, val;
+ int total;
val = Qnil;
handler = Ffind_file_name_handler (filename);
if (!NILP (handler))
{
- val = call3 (handler, Qinsert_file_contents, filename, visit);
+ val = call5 (handler, Qinsert_file_contents, filename, visit, beg, end);
st.st_mtime = 0;
goto handled;
}
if (st.st_size < 0)
error ("File size is negative");
+ if (!NILP (beg) || !NILP (end))
+ if (!NILP (visit))
+ error ("Attempt to visit less than an entire file");
+
+ if (!NILP (beg))
+ CHECK_NUMBER (beg, 0);
+ else
+ XFASTINT (beg) = 0;
+
+ if (!NILP (end))
+ CHECK_NUMBER (end, 0);
+ else
+ {
+ XSETINT (end, st.st_size);
+ if (XINT (end) != st.st_size)
+ error ("maximum buffer size exceeded");
+ }
+
+ total = XINT (end) - XINT (beg);
+
{
register Lisp_Object temp;
/* Make sure point-max won't overflow after this insertion. */
- XSET (temp, Lisp_Int, st.st_size + Z);
- if (st.st_size + Z != XINT (temp))
+ XSET (temp, Lisp_Int, total);
+ if (total != XINT (temp))
error ("maximum buffer size exceeded");
}
prepare_to_modify_buffer (point, point);
move_gap (point);
- if (GAP_SIZE < st.st_size)
- make_gap (st.st_size - GAP_SIZE);
-
+ if (GAP_SIZE < total)
+ make_gap (total - GAP_SIZE);
+
+ if (XINT (beg) != 0)
+ {
+ if (lseek (fd, XINT (beg), 0) < 0)
+ report_file_error ("Setting file position", Fcons (filename, Qnil));
+ }
+
while (1)
{
- int try = min (st.st_size - inserted, 64 << 10);
+ int try = min (total - inserted, 64 << 10);
int this;
/* Allow quitting out of the actual I/O. */
Fcons (make_number (inserted),
Qnil)));
}
-
+\f
DEFUN ("write-region", Fwrite_region, Swrite_region, 3, 5,
"r\nFWrite region to file: ",
"Write current region into specified file.\n\
if (!NILP (handler))
{
- Lisp_Object args[7];
Lisp_Object val;
- args[0] = handler;
- args[1] = Qwrite_region;
- args[2] = start;
- args[3] = end;
- args[4] = filename;
- args[5] = append;
- args[6] = visit;
- val = Ffuncall (7, args);
+ val = call6 (handler, Qwrite_region, start, end,
+ filename, append, visit);
/* Do this before reporting IO error
to avoid a "file has changed on disk" warning on
#ifdef HAVE_FSYNC
/* Note fsync appears to change the modtime on BSD4.2 (both vax and sun).
Disk full in NFS may be reported here. */
- if (fsync (desc) < 0)
+ /* mib says that closing the file will try to write as fast as NFS can do
+ it, and that means the fsync here is not crucial for autosave files. */
+ if (!auto_saving && fsync (desc) < 0)
failure = 1, save_errno = errno;
#endif
call the corresponding file handler. */
handler = Ffind_file_name_handler (filename);
if (!NILP (handler))
- return call3 (handler, Qfile_name_directory, filename, Qnil);
+ /* The handler can find the file name the same way we did. */
+ return call2 (handler, Qset_visited_file_modtime, Qnil);
else if (stat (XSTRING (filename)->data, &st) >= 0)
current_buffer->modtime = st.st_mtime;
}
tem = Fstring_equal (val, insdef);
if (!NILP (tem) && !NILP (defalt))
return defalt;
+ if (XSTRING (val)->size == 0 && NILP (insdef))
+ return defalt;
return Fsubstitute_in_file_name (val);
}
Qinsert_file_contents = intern ("insert-file-contents");
Qwrite_region = intern ("write-region");
Qverify_visited_file_modtime = intern ("verify-visited-file-modtime");
+ Qset_visited_file_modtime = intern ("set-visited-file-modtime");
staticpro (&Qexpand_file_name);
staticpro (&Qdirectory_file_name);