From d90a61ad78135be2eb28ed53c61acf804b80c843 Mon Sep 17 00:00:00 2001 From: edyfox Date: Fri, 29 Jun 2007 06:57:25 +0000 Subject: [PATCH] Synced with the latest branch. git-svn-id: https://vim.svn.sourceforge.net/svnroot/vim/trunk@317 2a77ed30-b011-0410-a7ad-c7884a0aa172 --- src/ex_cmds.c | 26 ++++++++++++++++++++++---- src/fileio.c | 41 +++++++++++++++++++++++++++++------------ src/ops.c | 4 +++- src/popupmnu.c | 2 +- src/proto/fileio.pro | 1 + src/quickfix.c | 2 +- src/version.c | 6 ++++++ 7 files changed, 63 insertions(+), 19 deletions(-) diff --git a/src/ex_cmds.c b/src/ex_cmds.c index 9c9f8565..5ca3dfd0 100644 --- a/src/ex_cmds.c +++ b/src/ex_cmds.c @@ -2912,22 +2912,35 @@ not_writing() } /* - * Check if a buffer is read-only. Ask for overruling in a dialog. - * Return TRUE and give an error message when the buffer is readonly. + * Check if a buffer is read-only (either 'readonly' option is set or file is + * read-only). Ask for overruling in a dialog. Return TRUE and give an error + * message when the buffer is readonly. */ static int check_readonly(forceit, buf) int *forceit; buf_T *buf; { - if (!*forceit && buf->b_p_ro) + struct stat st; + + /* Handle a file being readonly when the 'readonly' option is set or when + * the file exists and permissions are read-only. + * We will send 0777 to check_file_readonly(), as the "perm" variable is + * important for device checks but not here. */ + if (!*forceit && (buf->b_p_ro + || (mch_stat((char *)buf->b_ffname, &st) >= 0 + && check_file_readonly(buf->b_ffname, 0777)))) { #if defined(FEAT_GUI_DIALOG) || defined(FEAT_CON_DIALOG) if ((p_confirm || cmdmod.confirm) && buf->b_fname != NULL) { char_u buff[IOSIZE]; - dialog_msg(buff, _("'readonly' option is set for \"%s\".\nDo you wish to write anyway?"), + if (buf->b_p_ro) + dialog_msg(buff, _("'readonly' option is set for \"%s\".\nDo you wish to write anyway?"), + buf->b_fname); + else + dialog_msg(buff, _("File permissions of \"%s\" are read-only.\nIt may still be possible to write it.\nDo you wish to try?"), buf->b_fname); if (vim_dialog_yesno(VIM_QUESTION, NULL, buff, 2) == VIM_YES) @@ -2941,9 +2954,14 @@ check_readonly(forceit, buf) } else #endif + if (buf->b_p_ro) EMSG(_(e_readonly)); + else + EMSG2(_("E505: \"%s\" is read-only (add ! to override)"), + buf->b_fname); return TRUE; } + return FALSE; } diff --git a/src/fileio.c b/src/fileio.c index c44a08d3..6fd2799c 100644 --- a/src/fileio.c +++ b/src/fileio.c @@ -424,7 +424,7 @@ readfile(fname, sfname, from, lines_to_skip, lines_to_read, eap, flags) */ if (!p_odev && mch_nodetype(fname) == NODE_WRITABLE) { - filemess(curbuf, fname, (char_u *)_("is a device (disabled with 'opendevice' option"), 0); + filemess(curbuf, fname, (char_u *)_("is a device (disabled with 'opendevice' option)"), 0); msg_end(); msg_scroll = msg_save; return FAIL; @@ -2734,6 +2734,32 @@ set_file_time(fname, atime, mtime) #endif /* + * Return TRUE if a file appears to be read-only from the file permissions. + */ + int +check_file_readonly(fname, perm) + char_u *fname; /* full path to file */ + int perm; /* known permissions on file */ +{ +#ifndef USE_MCH_ACCESS + int fd = 0; +#endif + + return ( +#ifdef USE_MCH_ACCESS +# ifdef UNIX + (perm & 0222) == 0 || +# endif + mch_access((char *)fname, W_OK) +#else + (fd = mch_open((char *)fname, O_RDWR | O_EXTRA, 0)) < 0 + ? TRUE : (close(fd), FALSE) +#endif + ); +} + + +/* * buf_write() - write to file "fname" lines "start" through "end" * * We do our own buffering here because fwrite() is so slow. @@ -3219,17 +3245,8 @@ buf_write(buf, fname, sfname, start, end, eap, append, forceit, * Check if the file is really writable (when renaming the file to * make a backup we won't discover it later). */ - file_readonly = ( -# ifdef USE_MCH_ACCESS -# ifdef UNIX - (perm & 0222) == 0 || -# endif - mch_access((char *)fname, W_OK) -# else - (fd = mch_open((char *)fname, O_RDWR | O_EXTRA, 0)) < 0 - ? TRUE : (close(fd), FALSE) -# endif - ); + file_readonly = check_file_readonly(fname, (int)perm); + if (!forceit && file_readonly) { if (vim_strchr(p_cpo, CPO_FWRITE) != NULL) diff --git a/src/ops.c b/src/ops.c index ddc414b5..e8c69170 100644 --- a/src/ops.c +++ b/src/ops.c @@ -3404,7 +3404,9 @@ do_put(regname, dir, count, flags) #ifdef FEAT_VIRTUALEDIT col += curwin->w_cursor.coladd; - if (ve_flags == VE_ALL && curwin->w_cursor.coladd > 0) + if (ve_flags == VE_ALL + && (curwin->w_cursor.coladd > 0 + || endcol2 == curwin->w_cursor.col)) { if (dir == FORWARD && c == NUL) ++col; diff --git a/src/popupmnu.c b/src/popupmnu.c index 7d2e1379..eb4631a4 100644 --- a/src/popupmnu.c +++ b/src/popupmnu.c @@ -466,7 +466,7 @@ pum_set_selected(n, repeat) set_option_value((char_u *)"bh", 0L, (char_u *)"wipe", OPT_LOCAL); set_option_value((char_u *)"diff", 0L, - (char_u *)"", OPT_LOCAL); + NULL, OPT_LOCAL); } } if (res == OK) diff --git a/src/proto/fileio.pro b/src/proto/fileio.pro index a8c4142e..068117ad 100644 --- a/src/proto/fileio.pro +++ b/src/proto/fileio.pro @@ -2,6 +2,7 @@ void filemess __ARGS((buf_T *buf, char_u *name, char_u *s, int attr)); int readfile __ARGS((char_u *fname, char_u *sfname, linenr_T from, linenr_T lines_to_skip, linenr_T lines_to_read, exarg_T *eap, int flags)); int prep_exarg __ARGS((exarg_T *eap, buf_T *buf)); +int check_file_readonly __ARGS((char_u *fname, int perm)); int buf_write __ARGS((buf_T *buf, char_u *fname, char_u *sfname, linenr_T start, linenr_T end, exarg_T *eap, int append, int forceit, int reset_changed, int filtering)); void msg_add_fname __ARGS((buf_T *buf, char_u *fname)); void msg_add_lines __ARGS((int insert_space, long lnum, long nchars)); diff --git a/src/quickfix.c b/src/quickfix.c index 3b471323..1ae175b5 100644 --- a/src/quickfix.c +++ b/src/quickfix.c @@ -2331,7 +2331,7 @@ ex_copen(eap) set_option_value((char_u *)"bt", 0L, (char_u *)"quickfix", OPT_LOCAL); set_option_value((char_u *)"bh", 0L, (char_u *)"wipe", OPT_LOCAL); - set_option_value((char_u *)"diff", 0L, (char_u *)"", OPT_LOCAL); + set_option_value((char_u *)"diff", 0L, NULL, OPT_LOCAL); } /* Only set the height when still in the same tab page and there is no diff --git a/src/version.c b/src/version.c index b68beb09..42750d32 100644 --- a/src/version.c +++ b/src/version.c @@ -667,6 +667,12 @@ static char *(features[]) = static int included_patches[] = { /* Add new patch number below this line */ /**/ + 18, +/**/ + 17, +/**/ + 16, +/**/ 15, /**/ 14, -- 2.11.4.GIT