diff options
| author | Richard M. Stallman | 1995-10-01 07:14:42 +0000 |
|---|---|---|
| committer | Richard M. Stallman | 1995-10-01 07:14:42 +0000 |
| commit | 3ed15d97b1b252b500cb2fb58e7286c3c55178f2 (patch) | |
| tree | 699f8fbc38a835210afff62dc01a1555dc37171a /src | |
| parent | d7d7c1dd1b4355a4a70a6791377103c12dc27972 (diff) | |
| download | emacs-3ed15d97b1b252b500cb2fb58e7286c3c55178f2.tar.gz emacs-3ed15d97b1b252b500cb2fb58e7286c3c55178f2.zip | |
(barf_or_query_if_file_exists): New arg STATPTR. Callers changed.
(Fcopy_file): Error if input and output are the same file.
Diffstat (limited to 'src')
| -rw-r--r-- | src/fileio.c | 46 |
1 files changed, 37 insertions, 9 deletions
diff --git a/src/fileio.c b/src/fileio.c index cd2e9bbfe0f..f8469cbd821 100644 --- a/src/fileio.c +++ b/src/fileio.c | |||
| @@ -1788,11 +1788,20 @@ expand_and_dir_to_file (filename, defdir) | |||
| 1788 | return abspath; | 1788 | return abspath; |
| 1789 | } | 1789 | } |
| 1790 | 1790 | ||
| 1791 | /* Signal an error if the file ABSNAME already exists. | ||
| 1792 | If INTERACTIVE is nonzero, ask the user whether to proceed, | ||
| 1793 | and bypass the error if the user says to go ahead. | ||
| 1794 | QUERYSTRING is a name for the action that is being considered | ||
| 1795 | to alter the file. | ||
| 1796 | *STATPTR is used to store the stat information if the file exists. | ||
| 1797 | If the file does not exist, STATPTR->st_mode is set to 0. */ | ||
| 1798 | |||
| 1791 | void | 1799 | void |
| 1792 | barf_or_query_if_file_exists (absname, querystring, interactive) | 1800 | barf_or_query_if_file_exists (absname, querystring, interactive, statptr) |
| 1793 | Lisp_Object absname; | 1801 | Lisp_Object absname; |
| 1794 | unsigned char *querystring; | 1802 | unsigned char *querystring; |
| 1795 | int interactive; | 1803 | int interactive; |
| 1804 | struct stat *statptr; | ||
| 1796 | { | 1805 | { |
| 1797 | register Lisp_Object tem; | 1806 | register Lisp_Object tem; |
| 1798 | struct stat statbuf; | 1807 | struct stat statbuf; |
| @@ -1814,6 +1823,13 @@ barf_or_query_if_file_exists (absname, querystring, interactive) | |||
| 1814 | Fsignal (Qfile_already_exists, | 1823 | Fsignal (Qfile_already_exists, |
| 1815 | Fcons (build_string ("File already exists"), | 1824 | Fcons (build_string ("File already exists"), |
| 1816 | Fcons (absname, Qnil))); | 1825 | Fcons (absname, Qnil))); |
| 1826 | if (statptr) | ||
| 1827 | *statptr = statbuf; | ||
| 1828 | } | ||
| 1829 | else | ||
| 1830 | { | ||
| 1831 | if (statptr) | ||
| 1832 | statptr->st_mode = 0; | ||
| 1817 | } | 1833 | } |
| 1818 | return; | 1834 | return; |
| 1819 | } | 1835 | } |
| @@ -1833,7 +1849,7 @@ A prefix arg makes KEEP-TIME non-nil.") | |||
| 1833 | { | 1849 | { |
| 1834 | int ifd, ofd, n; | 1850 | int ifd, ofd, n; |
| 1835 | char buf[16 * 1024]; | 1851 | char buf[16 * 1024]; |
| 1836 | struct stat st; | 1852 | struct stat st, out_st; |
| 1837 | Lisp_Object handler; | 1853 | Lisp_Object handler; |
| 1838 | struct gcpro gcpro1, gcpro2; | 1854 | struct gcpro gcpro1, gcpro2; |
| 1839 | int count = specpdl_ptr - specpdl; | 1855 | int count = specpdl_ptr - specpdl; |
| @@ -1858,7 +1874,9 @@ A prefix arg makes KEEP-TIME non-nil.") | |||
| 1858 | if (NILP (ok_if_already_exists) | 1874 | if (NILP (ok_if_already_exists) |
| 1859 | || INTEGERP (ok_if_already_exists)) | 1875 | || INTEGERP (ok_if_already_exists)) |
| 1860 | barf_or_query_if_file_exists (newname, "copy to it", | 1876 | barf_or_query_if_file_exists (newname, "copy to it", |
| 1861 | INTEGERP (ok_if_already_exists)); | 1877 | INTEGERP (ok_if_already_exists), &out_st); |
| 1878 | else if (stat (XSTRING (newname)->data, &out_st) < 0) | ||
| 1879 | out_st.st_mode = 0; | ||
| 1862 | 1880 | ||
| 1863 | ifd = open (XSTRING (filename)->data, O_RDONLY); | 1881 | ifd = open (XSTRING (filename)->data, O_RDONLY); |
| 1864 | if (ifd < 0) | 1882 | if (ifd < 0) |
| @@ -1870,6 +1888,16 @@ A prefix arg makes KEEP-TIME non-nil.") | |||
| 1870 | copyable by us. */ | 1888 | copyable by us. */ |
| 1871 | input_file_statable_p = (fstat (ifd, &st) >= 0); | 1889 | input_file_statable_p = (fstat (ifd, &st) >= 0); |
| 1872 | 1890 | ||
| 1891 | #ifndef DOS_NT | ||
| 1892 | if (out_st.st_mode != 0 | ||
| 1893 | && st.st_dev == out_st.st_dev && st.st_ino == out_st.st_ino) | ||
| 1894 | { | ||
| 1895 | errno = 0; | ||
| 1896 | report_file_error ("Input and output files are the same", | ||
| 1897 | Fcons (filename, Fcons (newname, Qnil))); | ||
| 1898 | } | ||
| 1899 | #endif | ||
| 1900 | |||
| 1873 | #if defined (S_ISREG) && defined (S_ISLNK) | 1901 | #if defined (S_ISREG) && defined (S_ISLNK) |
| 1874 | if (input_file_statable_p) | 1902 | if (input_file_statable_p) |
| 1875 | { | 1903 | { |
| @@ -1879,7 +1907,7 @@ A prefix arg makes KEEP-TIME non-nil.") | |||
| 1879 | /* Get a better looking error message. */ | 1907 | /* Get a better looking error message. */ |
| 1880 | errno = EISDIR; | 1908 | errno = EISDIR; |
| 1881 | #endif /* EISDIR */ | 1909 | #endif /* EISDIR */ |
| 1882 | report_file_error ("Non-regular file", Fcons (filename, Qnil)); | 1910 | report_file_error ("Non-regular file", Fcons (filename, Qnil)); |
| 1883 | } | 1911 | } |
| 1884 | } | 1912 | } |
| 1885 | #endif /* S_ISREG && S_ISLNK */ | 1913 | #endif /* S_ISREG && S_ISLNK */ |
| @@ -1896,7 +1924,7 @@ A prefix arg makes KEEP-TIME non-nil.") | |||
| 1896 | #endif /* not MSDOS */ | 1924 | #endif /* not MSDOS */ |
| 1897 | #endif /* VMS */ | 1925 | #endif /* VMS */ |
| 1898 | if (ofd < 0) | 1926 | if (ofd < 0) |
| 1899 | report_file_error ("Opening output file", Fcons (newname, Qnil)); | 1927 | report_file_error ("Opening output file", Fcons (newname, Qnil)); |
| 1900 | 1928 | ||
| 1901 | record_unwind_protect (close_file_unwind, make_number (ofd)); | 1929 | record_unwind_protect (close_file_unwind, make_number (ofd)); |
| 1902 | 1930 | ||
| @@ -1904,7 +1932,7 @@ A prefix arg makes KEEP-TIME non-nil.") | |||
| 1904 | QUIT; | 1932 | QUIT; |
| 1905 | while ((n = read (ifd, buf, sizeof buf)) > 0) | 1933 | while ((n = read (ifd, buf, sizeof buf)) > 0) |
| 1906 | if (write (ofd, buf, n) != n) | 1934 | if (write (ofd, buf, n) != n) |
| 1907 | report_file_error ("I/O error", Fcons (newname, Qnil)); | 1935 | report_file_error ("I/O error", Fcons (newname, Qnil)); |
| 1908 | immediate_quit = 0; | 1936 | immediate_quit = 0; |
| 1909 | 1937 | ||
| 1910 | /* Closing the output clobbers the file times on some systems. */ | 1938 | /* Closing the output clobbers the file times on some systems. */ |
| @@ -2054,7 +2082,7 @@ This is what happens in interactive use with M-x.") | |||
| 2054 | if (NILP (ok_if_already_exists) | 2082 | if (NILP (ok_if_already_exists) |
| 2055 | || INTEGERP (ok_if_already_exists)) | 2083 | || INTEGERP (ok_if_already_exists)) |
| 2056 | barf_or_query_if_file_exists (newname, "rename to it", | 2084 | barf_or_query_if_file_exists (newname, "rename to it", |
| 2057 | INTEGERP (ok_if_already_exists)); | 2085 | INTEGERP (ok_if_already_exists), 0); |
| 2058 | #ifndef BSD4_1 | 2086 | #ifndef BSD4_1 |
| 2059 | if (0 > rename (XSTRING (filename)->data, XSTRING (newname)->data)) | 2087 | if (0 > rename (XSTRING (filename)->data, XSTRING (newname)->data)) |
| 2060 | #else | 2088 | #else |
| @@ -2134,7 +2162,7 @@ This is what happens in interactive use with M-x.") | |||
| 2134 | if (NILP (ok_if_already_exists) | 2162 | if (NILP (ok_if_already_exists) |
| 2135 | || INTEGERP (ok_if_already_exists)) | 2163 | || INTEGERP (ok_if_already_exists)) |
| 2136 | barf_or_query_if_file_exists (newname, "make it a new name", | 2164 | barf_or_query_if_file_exists (newname, "make it a new name", |
| 2137 | INTEGERP (ok_if_already_exists)); | 2165 | INTEGERP (ok_if_already_exists), 0); |
| 2138 | #ifdef WINDOWSNT | 2166 | #ifdef WINDOWSNT |
| 2139 | /* Windows does not support this operation. */ | 2167 | /* Windows does not support this operation. */ |
| 2140 | report_file_error ("Adding new name", Flist (2, &filename)); | 2168 | report_file_error ("Adding new name", Flist (2, &filename)); |
| @@ -2201,7 +2229,7 @@ This happens for interactive use with M-x.") | |||
| 2201 | if (NILP (ok_if_already_exists) | 2229 | if (NILP (ok_if_already_exists) |
| 2202 | || INTEGERP (ok_if_already_exists)) | 2230 | || INTEGERP (ok_if_already_exists)) |
| 2203 | barf_or_query_if_file_exists (linkname, "make it a link", | 2231 | barf_or_query_if_file_exists (linkname, "make it a link", |
| 2204 | INTEGERP (ok_if_already_exists)); | 2232 | INTEGERP (ok_if_already_exists), 0); |
| 2205 | if (0 > symlink (XSTRING (filename)->data, XSTRING (linkname)->data)) | 2233 | if (0 > symlink (XSTRING (filename)->data, XSTRING (linkname)->data)) |
| 2206 | { | 2234 | { |
| 2207 | /* If we didn't complain already, silently delete existing file. */ | 2235 | /* If we didn't complain already, silently delete existing file. */ |