1 /* vi:set ts=8 sts=4 sw=4: 2 * 3 * VIM - Vi IMproved by Bram Moolenaar 4 * 5 * Do ":help uganda" in Vim to read copying and usage conditions. 6 * Do ":help credits" in Vim to see a list of people who contributed. 7 * See README.txt for an overview of the Vim source code. 8 */ 9 10 /* 11 * fileio.c: read from and write to a file 12 */ 13 14 #if defined(MSDOS) || defined(WIN16) || defined(WIN32) || defined(_WIN64) 15 # include <io.h> /* for lseek(), must be before vim.h */ 16 #endif 17 18 #if defined __EMX__ 19 # include <io.h> /* for mktemp(), CJW 1997-12-03 */ 20 #endif 21 22 #include "vim.h" 23 24 #ifdef HAVE_FCNTL_H 25 # include <fcntl.h> 26 #endif 27 28 #ifdef __TANDEM 29 # include <limits.h> /* for SSIZE_MAX */ 30 #endif 31 32 #if defined(HAVE_UTIME) && defined(HAVE_UTIME_H) 33 # include <utime.h> /* for struct utimbuf */ 34 #endif 35 36 #define BUFSIZE 8192 /* size of normal write buffer */ 37 #define SMBUFSIZE 256 /* size of emergency write buffer */ 38 39 #ifdef FEAT_CRYPT 40 # define CRYPT_MAGIC "VimCrypt~01!" /* "01" is the version nr */ 41 # define CRYPT_MAGIC_LEN 12 /* must be multiple of 4! */ 42 #endif 43 44 /* Is there any system that doesn't have access()? */ 45 #ifndef MACOS_CLASSIC /* Not available on MacOS 9 */ 46 # define USE_MCH_ACCESS 47 #endif 48 49 #ifdef FEAT_MBYTE 50 static char_u *next_fenc __ARGS((char_u **pp)); 51 # ifdef FEAT_EVAL 52 static char_u *readfile_charconvert __ARGS((char_u *fname, char_u *fenc, int *fdp)); 53 # endif 54 #endif 55 #ifdef FEAT_VIMINFO 56 static void check_marks_read __ARGS((void)); 57 #endif 58 #ifdef FEAT_CRYPT 59 static char_u *check_for_cryptkey __ARGS((char_u *cryptkey, char_u *ptr, long *sizep, long *filesizep, int newfile)); 60 #endif 61 #ifdef UNIX 62 static void set_file_time __ARGS((char_u *fname, time_t atime, time_t mtime)); 63 #endif 64 static void msg_add_fname __ARGS((buf_T *, char_u *)); 65 static int msg_add_fileformat __ARGS((int eol_type)); 66 static void msg_add_lines __ARGS((int, long, long)); 67 static void msg_add_eol __ARGS((void)); 68 static int check_mtime __ARGS((buf_T *buf, struct stat *s)); 69 static int time_differs __ARGS((long t1, long t2)); 70 #ifdef FEAT_AUTOCMD 71 static int apply_autocmds_exarg __ARGS((EVENT_T event, char_u *fname, char_u *fname_io, int force, buf_T *buf, exarg_T *eap)); 72 #endif 73 74 #if defined(FEAT_CRYPT) || defined(FEAT_MBYTE) 75 # define HAS_BW_FLAGS 76 # define FIO_LATIN1 0x01 /* convert Latin1 */ 77 # define FIO_UTF8 0x02 /* convert UTF-8 */ 78 # define FIO_UCS2 0x04 /* convert UCS-2 */ 79 # define FIO_UCS4 0x08 /* convert UCS-4 */ 80 # define FIO_UTF16 0x10 /* convert UTF-16 */ 81 # ifdef WIN3264 82 # define FIO_CODEPAGE 0x20 /* convert MS-Windows codepage */ 83 # define FIO_PUT_CP(x) (((x) & 0xffff) << 16) /* put codepage in top word */ 84 # define FIO_GET_CP(x) (((x)>>16) & 0xffff) /* get codepage from top word */ 85 # endif 86 # ifdef MACOS_X 87 # define FIO_MACROMAN 0x20 /* convert MacRoman */ 88 # endif 89 # define FIO_ENDIAN_L 0x80 /* little endian */ 90 # define FIO_ENCRYPTED 0x1000 /* encrypt written bytes */ 91 # define FIO_NOCONVERT 0x2000 /* skip encoding conversion */ 92 # define FIO_UCSBOM 0x4000 /* check for BOM at start of file */ 93 # define FIO_ALL -1 /* allow all formats */ 94 #endif 95 96 /* When converting, a read() or write() may leave some bytes to be converted 97 * for the next call. The value is guessed... */ 98 #define CONV_RESTLEN 30 99 100 /* We have to guess how much a sequence of bytes may expand when converting 101 * with iconv() to be able to allocate a buffer. */ 102 #define ICONV_MULT 8 103 104 /* 105 * Structure to pass arguments from buf_write() to buf_write_bytes(). 106 */ 107 struct bw_info 108 { 109 int bw_fd; /* file descriptor */ 110 char_u *bw_buf; /* buffer with data to be written */ 111 int bw_len; /* lenght of data */ 112 #ifdef HAS_BW_FLAGS 113 int bw_flags; /* FIO_ flags */ 114 #endif 115 #ifdef FEAT_MBYTE 116 char_u bw_rest[CONV_RESTLEN]; /* not converted bytes */ 117 int bw_restlen; /* nr of bytes in bw_rest[] */ 118 int bw_first; /* first write call */ 119 char_u *bw_conv_buf; /* buffer for writing converted chars */ 120 int bw_conv_buflen; /* size of bw_conv_buf */ 121 int bw_conv_error; /* set for conversion error */ 122 # ifdef USE_ICONV 123 iconv_t bw_iconv_fd; /* descriptor for iconv() or -1 */ 124 # endif 125 #endif 126 }; 127 128 static int buf_write_bytes __ARGS((struct bw_info *ip)); 129 130 #ifdef FEAT_MBYTE 131 static int ucs2bytes __ARGS((unsigned c, char_u **pp, int flags)); 132 static int same_encoding __ARGS((char_u *a, char_u *b)); 133 static int get_fio_flags __ARGS((char_u *ptr)); 134 static char_u *check_for_bom __ARGS((char_u *p, long size, int *lenp, int flags)); 135 static int make_bom __ARGS((char_u *buf, char_u *name)); 136 # ifdef WIN3264 137 static int get_win_fio_flags __ARGS((char_u *ptr)); 138 # endif 139 # ifdef MACOS_X 140 static int get_mac_fio_flags __ARGS((char_u *ptr)); 141 # endif 142 #endif 143 static int move_lines __ARGS((buf_T *frombuf, buf_T *tobuf)); 144 145 static linenr_T write_no_eol_lnum = 0; /* non-zero lnum when last line of 146 next binary write should not have 147 an end-of-line */ 148 149 void 150 filemess(buf, name, s, attr) 151 buf_T *buf; 152 char_u *name; 153 char_u *s; 154 int attr; 155 { 156 int msg_scroll_save; 157 158 if (msg_silent != 0) 159 return; 160 msg_add_fname(buf, name); /* put file name in IObuff with quotes */ 161 /* If it's extremely long, truncate it. */ 162 if (STRLEN(IObuff) > IOSIZE - 80) 163 IObuff[IOSIZE - 80] = NUL; 164 STRCAT(IObuff, s); 165 /* 166 * For the first message may have to start a new line. 167 * For further ones overwrite the previous one, reset msg_scroll before 168 * calling filemess(). 169 */ 170 msg_scroll_save = msg_scroll; 171 if (shortmess(SHM_OVERALL) && !exiting && p_verbose == 0) 172 msg_scroll = FALSE; 173 if (!msg_scroll) /* wait a bit when overwriting an error msg */ 174 check_for_delay(FALSE); 175 msg_start(); 176 msg_scroll = msg_scroll_save; 177 msg_scrolled_ign = TRUE; 178 /* may truncate the message to avoid a hit-return prompt */ 179 msg_outtrans_attr(msg_may_trunc(FALSE, IObuff), attr); 180 msg_clr_eos(); 181 out_flush(); 182 msg_scrolled_ign = FALSE; 183 } 184 185 /* 186 * Read lines from file "fname" into the buffer after line "from". 187 * 188 * 1. We allocate blocks with lalloc, as big as possible. 189 * 2. Each block is filled with characters from the file with a single read(). 190 * 3. The lines are inserted in the buffer with ml_append(). 191 * 192 * (caller must check that fname != NULL, unless READ_STDIN is used) 193 * 194 * "lines_to_skip" is the number of lines that must be skipped 195 * "lines_to_read" is the number of lines that are appended 196 * When not recovering lines_to_skip is 0 and lines_to_read MAXLNUM. 197 * 198 * flags: 199 * READ_NEW starting to edit a new buffer 200 * READ_FILTER reading filter output 201 * READ_STDIN read from stdin instead of a file 202 * READ_BUFFER read from curbuf instead of a file (converting after reading 203 * stdin) 204 * READ_DUMMY read into a dummy buffer (to check if file contents changed) 205 * 206 * return FAIL for failure, OK otherwise 207 */ 208 int 209 readfile(fname, sfname, from, lines_to_skip, lines_to_read, eap, flags) 210 char_u *fname; 211 char_u *sfname; 212 linenr_T from; 213 linenr_T lines_to_skip; 214 linenr_T lines_to_read; 215 exarg_T *eap; /* can be NULL! */ 216 int flags; 217 { 218 int fd = 0; 219 int newfile = (flags & READ_NEW); 220 int check_readonly; 221 int filtering = (flags & READ_FILTER); 222 int read_stdin = (flags & READ_STDIN); 223 int read_buffer = (flags & READ_BUFFER); 224 linenr_T read_buf_lnum = 1; /* next line to read from curbuf */ 225 colnr_T read_buf_col = 0; /* next char to read from this line */ 226 char_u c; 227 linenr_T lnum = from; 228 char_u *ptr = NULL; /* pointer into read buffer */ 229 char_u *buffer = NULL; /* read buffer */ 230 char_u *new_buffer = NULL; /* init to shut up gcc */ 231 char_u *line_start = NULL; /* init to shut up gcc */ 232 int wasempty; /* buffer was empty before reading */ 233 colnr_T len; 234 long size = 0; 235 char_u *p; 236 long filesize = 0; 237 int skip_read = FALSE; 238 #ifdef FEAT_CRYPT 239 char_u *cryptkey = NULL; 240 #endif 241 int split = 0; /* number of split lines */ 242 #define UNKNOWN 0x0fffffff /* file size is unknown */ 243 linenr_T linecnt; 244 int error = FALSE; /* errors encountered */ 245 int ff_error = EOL_UNKNOWN; /* file format with errors */ 246 long linerest = 0; /* remaining chars in line */ 247 #ifdef UNIX 248 int perm = 0; 249 int swap_mode = -1; /* protection bits for swap file */ 250 #else 251 int perm; 252 #endif 253 int fileformat = 0; /* end-of-line format */ 254 int keep_fileformat = FALSE; 255 struct stat st; 256 int file_readonly; 257 linenr_T skip_count = 0; 258 linenr_T read_count = 0; 259 int msg_save = msg_scroll; 260 linenr_T read_no_eol_lnum = 0; /* non-zero lnum when last line of 261 * last read was missing the eol */ 262 int try_mac = (vim_strchr(p_ffs, 'm') != NULL); 263 int try_dos = (vim_strchr(p_ffs, 'd') != NULL); 264 int try_unix = (vim_strchr(p_ffs, 'x') != NULL); 265 int file_rewind = FALSE; 266 #ifdef FEAT_MBYTE 267 int can_retry; 268 int conv_error = FALSE; /* conversion error detected */ 269 int keep_dest_enc = FALSE; /* don't retry when char doesn't fit 270 in destination encoding */ 271 linenr_T illegal_byte = 0; /* line nr with illegal byte */ 272 char_u *tmpname = NULL; /* name of 'charconvert' output file */ 273 int fio_flags = 0; 274 char_u *fenc; /* fileencoding to use */ 275 int fenc_alloced; /* fenc_next is in allocated memory */ 276 char_u *fenc_next = NULL; /* next item in 'fencs' or NULL */ 277 int advance_fenc = FALSE; 278 long real_size = 0; 279 # ifdef USE_ICONV 280 iconv_t iconv_fd = (iconv_t)-1; /* descriptor for iconv() or -1 */ 281 # ifdef FEAT_EVAL 282 int did_iconv = FALSE; /* TRUE when iconv() failed and trying 283 'charconvert' next */ 284 # endif 285 # endif 286 int converted = FALSE; /* TRUE if conversion done */ 287 int notconverted = FALSE; /* TRUE if conversion wanted but it 288 wasn't possible */ 289 char_u conv_rest[CONV_RESTLEN]; 290 int conv_restlen = 0; /* nr of bytes in conv_rest[] */ 291 #endif 292 293 #ifdef FEAT_AUTOCMD 294 write_no_eol_lnum = 0; /* in case it was set by the previous read */ 295 #endif 296 297 /* 298 * If there is no file name yet, use the one for the read file. 299 * BF_NOTEDITED is set to reflect this. 300 * Don't do this for a read from a filter. 301 * Only do this when 'cpoptions' contains the 'f' flag. 302 */ 303 if (curbuf->b_ffname == NULL 304 && !filtering 305 && fname != NULL 306 && vim_strchr(p_cpo, CPO_FNAMER) != NULL 307 && !(flags & READ_DUMMY)) 308 { 309 if (setfname(curbuf, fname, sfname, FALSE) == OK) 310 curbuf->b_flags |= BF_NOTEDITED; 311 } 312 313 /* 314 * For Unix: Use the short file name whenever possible. 315 * Avoids problems with networks and when directory names are changed. 316 * Don't do this for MS-DOS, a "cd" in a sub-shell may have moved us to 317 * another directory, which we don't detect. 318 */ 319 if (sfname == NULL) 320 sfname = fname; 321 #if defined(UNIX) || defined(__EMX__) 322 fname = sfname; 323 #endif 324 325 #ifdef FEAT_AUTOCMD 326 /* 327 * The BufReadCmd and FileReadCmd events intercept the reading process by 328 * executing the associated commands instead. 329 */ 330 if (!filtering && !read_stdin && !read_buffer) 331 { 332 pos_T pos; 333 334 pos = curbuf->b_op_start; 335 336 /* Set '[ mark to the line above where the lines go (line 1 if zero). */ 337 curbuf->b_op_start.lnum = ((from == 0) ? 1 : from); 338 curbuf->b_op_start.col = 0; 339 340 if (newfile) 341 { 342 if (apply_autocmds_exarg(EVENT_BUFREADCMD, NULL, sfname, 343 FALSE, curbuf, eap)) 344 #ifdef FEAT_EVAL 345 return aborting() ? FAIL : OK; 346 #else 347 return OK; 348 #endif 349 } 350 else if (apply_autocmds_exarg(EVENT_FILEREADCMD, sfname, sfname, 351 FALSE, NULL, eap)) 352 #ifdef FEAT_EVAL 353 return aborting() ? FAIL : OK; 354 #else 355 return OK; 356 #endif 357 358 curbuf->b_op_start = pos; 359 } 360 #endif 361 362 if ((shortmess(SHM_OVER) || curbuf->b_help) && p_verbose == 0) 363 msg_scroll = FALSE; /* overwrite previous file message */ 364 else 365 msg_scroll = TRUE; /* don't overwrite previous file message */ 366 367 /* 368 * If the name ends in a path separator, we can't open it. Check here, 369 * because reading the file may actually work, but then creating the swap 370 * file may destroy it! Reported on MS-DOS and Win 95. 371 * If the name is too long we might crash further on, quit here. 372 */ 373 if (fname != NULL 374 && *fname != NUL 375 && (vim_ispathsep(*(fname + STRLEN(fname) - 1)) 376 || STRLEN(fname) >= MAXPATHL)) 377 { 378 filemess(curbuf, fname, (char_u *)_("Illegal file name"), 0); 379 msg_end(); 380 msg_scroll = msg_save; 381 return FAIL; 382 } 383 384 #ifdef UNIX 385 /* 386 * On Unix it is possible to read a directory, so we have to 387 * check for it before the mch_open(). 388 */ 389 if (!read_stdin && !read_buffer) 390 { 391 perm = mch_getperm(fname); 392 if (perm >= 0 && !S_ISREG(perm) /* not a regular file ... */ 393 # ifdef S_ISFIFO 394 && !S_ISFIFO(perm) /* ... or fifo */ 395 # endif 396 # ifdef S_ISSOCK 397 && !S_ISSOCK(perm) /* ... or socket */ 398 # endif 399 ) 400 { 401 if (S_ISDIR(perm)) 402 filemess(curbuf, fname, (char_u *)_("is a directory"), 0); 403 else 404 filemess(curbuf, fname, (char_u *)_("is not a file"), 0); 405 msg_end(); 406 msg_scroll = msg_save; 407 return FAIL; 408 } 409 } 410 #endif 411 412 /* set default 'fileformat' */ 413 if (newfile) 414 { 415 if (eap != NULL && eap->force_ff != 0) 416 set_fileformat(get_fileformat_force(curbuf, eap), OPT_LOCAL); 417 else if (*p_ffs != NUL) 418 set_fileformat(default_fileformat(), OPT_LOCAL); 419 } 420 421 /* set or reset 'binary' */ 422 if (eap != NULL && eap->force_bin != 0) 423 { 424 int oldval = curbuf->b_p_bin; 425 426 curbuf->b_p_bin = (eap->force_bin == FORCE_BIN); 427 set_options_bin(oldval, curbuf->b_p_bin, OPT_LOCAL); 428 } 429 430 /* 431 * When opening a new file we take the readonly flag from the file. 432 * Default is r/w, can be set to r/o below. 433 * Don't reset it when in readonly mode 434 * Only set/reset b_p_ro when BF_CHECK_RO is set. 435 */ 436 check_readonly = (newfile && (curbuf->b_flags & BF_CHECK_RO)); 437 if (check_readonly && !readonlymode) /* default: set file not readonly */ 438 curbuf->b_p_ro = FALSE; 439 440 if (newfile && !read_stdin && !read_buffer) 441 { 442 /* Remember time of file. 443 * For RISCOS, also remember the filetype. 444 */ 445 if (mch_stat((char *)fname, &st) >= 0) 446 { 447 buf_store_time(curbuf, &st, fname); 448 curbuf->b_mtime_read = curbuf->b_mtime; 449 450 #if defined(RISCOS) && defined(FEAT_OSFILETYPE) 451 /* Read the filetype into the buffer local filetype option. */ 452 mch_read_filetype(fname); 453 #endif 454 #ifdef UNIX 455 /* 456 * Use the protection bits of the original file for the swap file. 457 * This makes it possible for others to read the name of the 458 * edited file from the swapfile, but only if they can read the 459 * edited file. 460 * Remove the "write" and "execute" bits for group and others 461 * (they must not write the swapfile). 462 * Add the "read" and "write" bits for the user, otherwise we may 463 * not be able to write to the file ourselves. 464 * Setting the bits is done below, after creating the swap file. 465 */ 466 swap_mode = (st.st_mode & 0644) | 0600; 467 #endif 468 #ifdef FEAT_CW_EDITOR 469 /* Get the FSSpec on MacOS 470 * TODO: Update it properly when the buffer name changes 471 */ 472 (void)GetFSSpecFromPath(curbuf->b_ffname, &curbuf->b_FSSpec); 473 #endif 474 #ifdef VMS 475 curbuf->b_fab_rfm = st.st_fab_rfm; 476 #endif 477 } 478 else 479 { 480 curbuf->b_mtime = 0; 481 curbuf->b_mtime_read = 0; 482 curbuf->b_orig_size = 0; 483 curbuf->b_orig_mode = 0; 484 } 485 486 /* Reset the "new file" flag. It will be set again below when the 487 * file doesn't exist. */ 488 curbuf->b_flags &= ~(BF_NEW | BF_NEW_W); 489 } 490 491 /* 492 * for UNIX: check readonly with perm and mch_access() 493 * for RISCOS: same as Unix, otherwise file gets re-datestamped! 494 * for MSDOS and Amiga: check readonly by trying to open the file for writing 495 */ 496 file_readonly = FALSE; 497 if (read_stdin) 498 { 499 #if defined(MSDOS) || defined(MSWIN) || defined(OS2) 500 /* Force binary I/O on stdin to avoid CR-LF -> LF conversion. */ 501 setmode(0, O_BINARY); 502 #endif 503 } 504 else if (!read_buffer) 505 { 506 #ifdef USE_MCH_ACCESS 507 if ( 508 # ifdef UNIX 509 !(perm & 0222) || 510 # endif 511 mch_access((char *)fname, W_OK)) 512 file_readonly = TRUE; 513 fd = mch_open((char *)fname, O_RDONLY | O_EXTRA, 0); 514 #else 515 if (!newfile 516 || readonlymode 517 || (fd = mch_open((char *)fname, O_RDWR | O_EXTRA, 0)) < 0) 518 { 519 file_readonly = TRUE; 520 /* try to open ro */ 521 fd = mch_open((char *)fname, O_RDONLY | O_EXTRA, 0); 522 } 523 #endif 524 } 525 526 if (fd < 0) /* cannot open at all */ 527 { 528 #ifndef UNIX 529 int isdir_f; 530 #endif 531 msg_scroll = msg_save; 532 #ifndef UNIX 533 /* 534 * On MSDOS and Amiga we can't open a directory, check here. 535 */ 536 isdir_f = (mch_isdir(fname)); 537 perm = mch_getperm(fname); /* check if the file exists */ 538 if (isdir_f) 539 { 540 filemess(curbuf, sfname, (char_u *)_("is a directory"), 0); 541 curbuf->b_p_ro = TRUE; /* must use "w!" now */ 542 } 543 else 544 #endif 545 if (newfile) 546 { 547 if (perm < 0) 548 { 549 /* 550 * Set the 'new-file' flag, so that when the file has 551 * been created by someone else, a ":w" will complain. 552 */ 553 curbuf->b_flags |= BF_NEW; 554 555 /* Create a swap file now, so that other Vims are warned 556 * that we are editing this file. Don't do this for a 557 * "nofile" or "nowrite" buffer type. */ 558 #ifdef FEAT_QUICKFIX 559 if (!bt_dontwrite(curbuf)) 560 #endif 561 check_need_swap(newfile); 562 filemess(curbuf, sfname, (char_u *)_("[New File]"), 0); 563 #ifdef FEAT_VIMINFO 564 /* Even though this is a new file, it might have been 565 * edited before and deleted. Get the old marks. */ 566 check_marks_read(); 567 #endif 568 #ifdef FEAT_MBYTE 569 if (eap != NULL && eap->force_enc != 0) 570 { 571 /* set forced 'fileencoding' */ 572 fenc = enc_canonize(eap->cmd + eap->force_enc); 573 if (fenc != NULL) 574 set_string_option_direct((char_u *)"fenc", -1, 575 fenc, OPT_FREE|OPT_LOCAL); 576 vim_free(fenc); 577 } 578 #endif 579 #ifdef FEAT_AUTOCMD 580 apply_autocmds_exarg(EVENT_BUFNEWFILE, sfname, sfname, 581 FALSE, curbuf, eap); 582 #endif 583 /* remember the current fileformat */ 584 save_file_ff(curbuf); 585 586 #if defined(FEAT_AUTOCMD) && defined(FEAT_EVAL) 587 if (aborting()) /* autocmds may abort script processing */ 588 return FAIL; 589 #endif 590 return OK; /* a new file is not an error */ 591 } 592 else 593 { 594 filemess(curbuf, sfname, 595 (char_u *)_("[Permission Denied]"), 0); 596 curbuf->b_p_ro = TRUE; /* must use "w!" now */ 597 } 598 } 599 600 return FAIL; 601 } 602 603 /* 604 * Only set the 'ro' flag for readonly files the first time they are 605 * loaded. Help files always get readonly mode 606 */ 607 if ((check_readonly && file_readonly) || curbuf->b_help) 608 curbuf->b_p_ro = TRUE; 609 610 if (newfile) 611 { 612 curbuf->b_p_eol = TRUE; 613 curbuf->b_start_eol = TRUE; 614 #ifdef FEAT_MBYTE 615 curbuf->b_p_bomb = FALSE; 616 #endif 617 } 618 619 /* Create a swap file now, so that other Vims are warned that we are 620 * editing this file. 621 * Don't do this for a "nofile" or "nowrite" buffer type. */ 622 #ifdef FEAT_QUICKFIX 623 if (!bt_dontwrite(curbuf)) 624 #endif 625 { 626 check_need_swap(newfile); 627 #ifdef UNIX 628 /* Set swap file protection bits after creating it. */ 629 if (swap_mode > 0 && curbuf->b_ml.ml_mfp->mf_fname != NULL) 630 (void)mch_setperm(curbuf->b_ml.ml_mfp->mf_fname, (long)swap_mode); 631 #endif 632 } 633 634 #if defined(FEAT_GUI_DIALOG) || defined(FEAT_CON_DIALOG) 635 /* If "Quit" selected at ATTENTION dialog, don't load the file */ 636 if (swap_exists_action == SEA_QUIT) 637 { 638 if (!read_buffer && !read_stdin) 639 close(fd); 640 return FAIL; 641 } 642 #endif 643 644 ++no_wait_return; /* don't wait for return yet */ 645 646 /* 647 * Set '[ mark to the line above where the lines go (line 1 if zero). 648 */ 649 curbuf->b_op_start.lnum = ((from == 0) ? 1 : from); 650 curbuf->b_op_start.col = 0; 651 652 #ifdef FEAT_AUTOCMD 653 if (!read_buffer) 654 { 655 int m = msg_scroll; 656 int n = msg_scrolled; 657 buf_T *old_curbuf = curbuf; 658 659 /* 660 * The file must be closed again, the autocommands may want to change 661 * the file before reading it. 662 */ 663 if (!read_stdin) 664 close(fd); /* ignore errors */ 665 666 /* 667 * The output from the autocommands should not overwrite anything and 668 * should not be overwritten: Set msg_scroll, restore its value if no 669 * output was done. 670 */ 671 msg_scroll = TRUE; 672 if (filtering) 673 apply_autocmds_exarg(EVENT_FILTERREADPRE, NULL, sfname, 674 FALSE, curbuf, eap); 675 else if (read_stdin) 676 apply_autocmds_exarg(EVENT_STDINREADPRE, NULL, sfname, 677 FALSE, curbuf, eap); 678 else if (newfile) 679 apply_autocmds_exarg(EVENT_BUFREADPRE, NULL, sfname, 680 FALSE, curbuf, eap); 681 else 682 apply_autocmds_exarg(EVENT_FILEREADPRE, sfname, sfname, 683 FALSE, NULL, eap); 684 if (msg_scrolled == n) 685 msg_scroll = m; 686 687 #ifdef FEAT_EVAL 688 if (aborting()) /* autocmds may abort script processing */ 689 { 690 --no_wait_return; 691 msg_scroll = msg_save; 692 curbuf->b_p_ro = TRUE; /* must use "w!" now */ 693 return FAIL; 694 } 695 #endif 696 /* 697 * Don't allow the autocommands to change the current buffer. 698 * Try to re-open the file. 699 */ 700 if (!read_stdin && (curbuf != old_curbuf 701 || (fd = mch_open((char *)fname, O_RDONLY | O_EXTRA, 0)) < 0)) 702 { 703 --no_wait_return; 704 msg_scroll = msg_save; 705 if (fd < 0) 706 EMSG(_("E200: *ReadPre autocommands made the file unreadable")); 707 else 708 EMSG(_("E201: *ReadPre autocommands must not change current buffer")); 709 curbuf->b_p_ro = TRUE; /* must use "w!" now */ 710 return FAIL; 711 } 712 } 713 #endif /* FEAT_AUTOCMD */ 714 715 /* Autocommands may add lines to the file, need to check if it is empty */ 716 wasempty = (curbuf->b_ml.ml_flags & ML_EMPTY); 717 718 if (!recoverymode && !filtering && !(flags & READ_DUMMY)) 719 { 720 /* 721 * Show the user that we are busy reading the input. Sometimes this 722 * may take a while. When reading from stdin another program may 723 * still be running, don't move the cursor to the last line, unless 724 * always using the GUI. 725 */ 726 if (read_stdin) 727 { 728 #ifndef ALWAYS_USE_GUI 729 mch_msg(_("Vim: Reading from stdin...\n")); 730 #endif 731 #ifdef FEAT_GUI 732 /* Also write a message in the GUI window, if there is one. */ 733 if (gui.in_use && !gui.dying && !gui.starting) 734 { 735 p = (char_u *)_("Reading from stdin..."); 736 gui_write(p, (int)STRLEN(p)); 737 } 738 #endif 739 } 740 else if (!read_buffer) 741 filemess(curbuf, sfname, (char_u *)"", 0); 742 } 743 744 msg_scroll = FALSE; /* overwrite the file message */ 745 746 /* 747 * Set linecnt now, before the "retry" caused by a wrong guess for 748 * fileformat, and after the autocommands, which may change them. 749 */ 750 linecnt = curbuf->b_ml.ml_line_count; 751 752 #ifdef FEAT_MBYTE 753 /* 754 * Decide which 'encoding' to use first. 755 */ 756 if (eap != NULL && eap->force_enc != 0) 757 { 758 fenc = enc_canonize(eap->cmd + eap->force_enc); 759 fenc_alloced = TRUE; 760 } 761 else if (curbuf->b_p_bin) 762 { 763 fenc = (char_u *)""; /* binary: don't convert */ 764 fenc_alloced = FALSE; 765 } 766 else if (curbuf->b_help) 767 { 768 char_u firstline[80]; 769 770 /* Help files are either utf-8 or latin1. Try utf-8 first, if this 771 * fails it must be latin1. 772 * Always do this when 'encoding' is "utf-8". Otherwise only do 773 * this when needed to avoid [converted] remarks all the time. 774 * It is needed when the first line contains non-ASCII characters. 775 * That is only in *.??x files. */ 776 fenc = (char_u *)"latin1"; 777 c = enc_utf8; 778 if (!c && !read_stdin && TOLOWER_ASC(fname[STRLEN(fname) - 1]) == 'x') 779 { 780 /* Read the first line (and a bit more). Immediately rewind to 781 * the start of the file. If the read() fails "len" is -1. */ 782 len = vim_read(fd, firstline, 80); 783 lseek(fd, (off_t)0L, SEEK_SET); 784 for (p = firstline; p < firstline + len; ++p) 785 if (*p >= 0x80) 786 { 787 c = TRUE; 788 break; 789 } 790 } 791 792 if (c) 793 { 794 fenc_next = fenc; 795 fenc = (char_u *)"utf-8"; 796 797 /* When the file is utf-8 but a character doesn't fit in 798 * 'encoding' don't retry. In help text editing utf-8 bytes 799 * doesn't make sense. */ 800 keep_dest_enc = TRUE; 801 } 802 fenc_alloced = FALSE; 803 } 804 else if (*p_fencs == NUL) 805 { 806 fenc = curbuf->b_p_fenc; /* use format from buffer */ 807 fenc_alloced = FALSE; 808 } 809 else 810 { 811 fenc_next = p_fencs; /* try items in 'fileencodings' */ 812 fenc = next_fenc(&fenc_next); 813 fenc_alloced = TRUE; 814 } 815 #endif 816 817 /* 818 * Jump back here to retry reading the file in different ways. 819 * Reasons to retry: 820 * - encoding conversion failed: try another one from "fenc_next" 821 * - BOM detected and fenc was set, need to setup conversion 822 * - "fileformat" check failed: try another 823 * 824 * Variables set for special retry actions: 825 * "file_rewind" Rewind the file to start reading it again. 826 * "advance_fenc" Advance "fenc" using "fenc_next". 827 * "skip_read" Re-use already read bytes (BOM detected). 828 * "did_iconv" iconv() conversion failed, try 'charconvert'. 829 * "keep_fileformat" Don't reset "fileformat". 830 * 831 * Other status indicators: 832 * "tmpname" When != NULL did conversion with 'charconvert'. 833 * Output file has to be deleted afterwards. 834 * "iconv_fd" When != -1 did conversion with iconv(). 835 */ 836 retry: 837 838 if (file_rewind) 839 { 840 if (read_buffer) 841 { 842 read_buf_lnum = 1; 843 read_buf_col = 0; 844 } 845 else if (read_stdin || lseek(fd, (off_t)0L, SEEK_SET) != 0) 846 { 847 /* Can't rewind the file, give up. */ 848 error = TRUE; 849 goto failed; 850 } 851 /* Delete the previously read lines. */ 852 while (lnum > from) 853 ml_delete(lnum--, FALSE); 854 file_rewind = FALSE; 855 #ifdef FEAT_MBYTE 856 if (newfile) 857 curbuf->b_p_bomb = FALSE; 858 conv_error = FALSE; 859 #endif 860 } 861 862 /* 863 * When retrying with another "fenc" and the first time "fileformat" 864 * will be reset. 865 */ 866 if (keep_fileformat) 867 keep_fileformat = FALSE; 868 else 869 { 870 if (eap != NULL && eap->force_ff != 0) 871 fileformat = get_fileformat_force(curbuf, eap); 872 else if (curbuf->b_p_bin) 873 fileformat = EOL_UNIX; /* binary: use Unix format */ 874 else if (*p_ffs == NUL) 875 fileformat = get_fileformat(curbuf);/* use format from buffer */ 876 else 877 fileformat = EOL_UNKNOWN; /* detect from file */ 878 } 879 880 #ifdef FEAT_MBYTE 881 # ifdef USE_ICONV 882 if (iconv_fd != (iconv_t)-1) 883 { 884 /* aborted conversion with iconv(), close the descriptor */ 885 iconv_close(iconv_fd); 886 iconv_fd = (iconv_t)-1; 887 } 888 # endif 889 890 if (advance_fenc) 891 { 892 /* 893 * Try the next entry in 'fileencodings'. 894 */ 895 advance_fenc = FALSE; 896 897 if (eap != NULL && eap->force_enc != 0) 898 { 899 /* Conversion given with "++cc=" wasn't possible, read 900 * without conversion. */ 901 notconverted = TRUE; 902 conv_error = FALSE; 903 if (fenc_alloced) 904 vim_free(fenc); 905 fenc = (char_u *)""; 906 fenc_alloced = FALSE; 907 } 908 else 909 { 910 if (fenc_alloced) 911 vim_free(fenc); 912 if (fenc_next != NULL) 913 { 914 fenc = next_fenc(&fenc_next); 915 fenc_alloced = (fenc_next != NULL); 916 } 917 else 918 { 919 fenc = (char_u *)""; 920 fenc_alloced = FALSE; 921 } 922 } 923 if (tmpname != NULL) 924 { 925 mch_remove(tmpname); /* delete converted file */ 926 vim_free(tmpname); 927 tmpname = NULL; 928 } 929 } 930 931 /* 932 * Conversion is required when the encoding of the file is different 933 * from 'encoding' or 'encoding' is UTF-16, UCS-2 or UCS-4 (requires 934 * conversion to UTF-8). 935 */ 936 fio_flags = 0; 937 converted = (*fenc != NUL && !same_encoding(p_enc, fenc)); 938 if (converted || enc_unicode != 0) 939 { 940 941 /* "ucs-bom" means we need to check the first bytes of the file 942 * for a BOM. */ 943 if (STRCMP(fenc, ENC_UCSBOM) == 0) 944 fio_flags = FIO_UCSBOM; 945 946 /* 947 * Check if UCS-2/4 or Latin1 to UTF-8 conversion needs to be 948 * done. This is handled below after read(). Prepare the 949 * fio_flags to avoid having to parse the string each time. 950 * Also check for Unicode to Latin1 conversion, because iconv() 951 * appears not to handle this correctly. This works just like 952 * conversion to UTF-8 except how the resulting character is put in 953 * the buffer. 954 */ 955 else if (enc_utf8 || STRCMP(p_enc, "latin1") == 0) 956 fio_flags = get_fio_flags(fenc); 957 958 # ifdef WIN3264 959 /* 960 * Conversion from an MS-Windows codepage to UTF-8 or another codepage 961 * is handled with MultiByteToWideChar(). 962 */ 963 if (fio_flags == 0) 964 fio_flags = get_win_fio_flags(fenc); 965 # endif 966 967 # ifdef MACOS_X 968 /* Conversion from Apple MacRoman to latin1 or UTF-8 */ 969 if (fio_flags == 0) 970 fio_flags = get_mac_fio_flags(fenc); 971 # endif 972 973 # ifdef USE_ICONV 974 /* 975 * Try using iconv() if we can't convert internally. 976 */ 977 if (fio_flags == 0 978 # ifdef FEAT_EVAL 979 && !did_iconv 980 # endif 981 ) 982 iconv_fd = (iconv_t)my_iconv_open( 983 enc_utf8 ? (char_u *)"utf-8" : p_enc, fenc); 984 # endif 985 986 # ifdef FEAT_EVAL 987 /* 988 * Use the 'charconvert' expression when conversion is required 989 * and we can't do it internally or with iconv(). 990 */ 991 if (fio_flags == 0 && !read_stdin && !read_buffer && *p_ccv != NUL 992 # ifdef USE_ICONV 993 && iconv_fd == (iconv_t)-1 994 # endif 995 ) 996 { 997 # ifdef USE_ICONV 998 did_iconv = FALSE; 999 # endif 1000 /* Skip conversion when it's already done (retry for wrong 1001 * "fileformat"). */ 1002 if (tmpname == NULL) 1003 { 1004 tmpname = readfile_charconvert(fname, fenc, &fd); 1005 if (tmpname == NULL) 1006 { 1007 /* Conversion failed. Try another one. */ 1008 advance_fenc = TRUE; 1009 if (fd < 0) 1010 { 1011 /* Re-opening the original file failed! */ 1012 EMSG(_("E202: Conversion made file unreadable!")); 1013 error = TRUE; 1014 goto failed; 1015 } 1016 goto retry; 1017 } 1018 } 1019 } 1020 else 1021 # endif 1022 { 1023 if (fio_flags == 0 1024 # ifdef USE_ICONV 1025 && iconv_fd == (iconv_t)-1 1026 # endif 1027 ) 1028 { 1029 /* Conversion wanted but we can't. 1030 * Try the next conversion in 'fileencodings' */ 1031 advance_fenc = TRUE; 1032 goto retry; 1033 } 1034 } 1035 } 1036 1037 /* Set can_retry when it's possible to rewind the file and try with 1038 * another "fenc" value. It's FALSE when no other "fenc" to try, reading 1039 * stdin or "fenc" was specified with "++enc=". */ 1040 can_retry = (*fenc != NUL && !read_stdin 1041 && (eap == NULL || eap->force_enc == 0)); 1042 #endif 1043 1044 if (!skip_read) 1045 { 1046 linerest = 0; 1047 filesize = 0; 1048 skip_count = lines_to_skip; 1049 read_count = lines_to_read; 1050 #ifdef FEAT_MBYTE 1051 conv_restlen = 0; 1052 #endif 1053 } 1054 1055 while (!error && !got_int) 1056 { 1057 /* 1058 * We allocate as much space for the file as we can get, plus 1059 * space for the old line plus room for one terminating NUL. 1060 * The amount is limited by the fact that read() only can read 1061 * upto max_unsigned characters (and other things). 1062 */ 1063 #if SIZEOF_INT <= 2 1064 if (linerest >= 0x7ff0) 1065 { 1066 ++split; 1067 *ptr = NL; /* split line by inserting a NL */ 1068 size = 1; 1069 } 1070 else 1071 #endif 1072 { 1073 if (!skip_read) 1074 { 1075 #if SIZEOF_INT > 2 1076 # ifdef __TANDEM 1077 size = SSIZE_MAX; /* use max I/O size, 52K */ 1078 # else 1079 size = 0x10000L; /* use buffer >= 64K */ 1080 # endif 1081 #else 1082 size = 0x7ff0L - linerest; /* limit buffer to 32K */ 1083 #endif 1084 1085 for ( ; size >= 10; size = (long_u)size >> 1) 1086 { 1087 if ((new_buffer = lalloc((long_u)(size + linerest + 1), 1088 FALSE)) != NULL) 1089 break; 1090 } 1091 if (new_buffer == NULL) 1092 { 1093 do_outofmem_msg((long_u)(size * 2 + linerest + 1)); 1094 error = TRUE; 1095 break; 1096 } 1097 if (linerest) /* copy characters from the previous buffer */ 1098 mch_memmove(new_buffer, ptr - linerest, (size_t)linerest); 1099 vim_free(buffer); 1100 buffer = new_buffer; 1101 ptr = buffer + linerest; 1102 line_start = buffer; 1103 1104 #ifdef FEAT_MBYTE 1105 /* May need room to translate into. 1106 * For iconv() we don't really know the required space, use a 1107 * factor ICONV_MULT. 1108 * latin1 to utf-8: 1 byte becomes up to 2 bytes 1109 * utf-16 to utf-8: 2 bytes become up to 3 bytes, 4 bytes 1110 * become up to 4 bytes, size must be multiple of 2 1111 * ucs-2 to utf-8: 2 bytes become up to 3 bytes, size must be 1112 * multiple of 2 1113 * ucs-4 to utf-8: 4 bytes become up to 6 bytes, size must be 1114 * multiple of 4 */ 1115 real_size = size; 1116 # ifdef USE_ICONV 1117 if (iconv_fd != (iconv_t)-1) 1118 size = size / ICONV_MULT; 1119 else 1120 # endif 1121 if (fio_flags & FIO_LATIN1) 1122 size = size / 2; 1123 else if (fio_flags & (FIO_UCS2 | FIO_UTF16)) 1124 size = (size * 2 / 3) & ~1; 1125 else if (fio_flags & FIO_UCS4) 1126 size = (size * 2 / 3) & ~3; 1127 else if (fio_flags == FIO_UCSBOM) 1128 size = size / ICONV_MULT; /* worst case */ 1129 # ifdef WIN3264 1130 else if (fio_flags & FIO_CODEPAGE) 1131 size = size / ICONV_MULT; /* also worst case */ 1132 # endif 1133 # ifdef MACOS_X 1134 else if (fio_flags & FIO_MACROMAN) 1135 size = size / ICONV_MULT; /* also worst case */ 1136 # endif 1137 #endif 1138 1139 #ifdef FEAT_MBYTE 1140 if (conv_restlen > 0) 1141 { 1142 /* Insert unconverted bytes from previous line. */ 1143 mch_memmove(ptr, conv_rest, conv_restlen); 1144 ptr += conv_restlen; 1145 size -= conv_restlen; 1146 } 1147 #endif 1148 1149 if (read_buffer) 1150 { 1151 /* 1152 * Read bytes from curbuf. Used for converting text read 1153 * from stdin. 1154 */ 1155 if (read_buf_lnum > from) 1156 size = 0; 1157 else 1158 { 1159 int n, ni; 1160 long tlen; 1161 1162 tlen = 0; 1163 for (;;) 1164 { 1165 p = ml_get(read_buf_lnum) + read_buf_col; 1166 n = (int)STRLEN(p); 1167 if ((int)tlen + n + 1 > size) 1168 { 1169 /* Filled up to "size", append partial line. 1170 * Change NL to NUL to reverse the effect done 1171 * below. */ 1172 n = size - tlen; 1173 for (ni = 0; ni < n; ++ni) 1174 { 1175 if (p[ni] == NL) 1176 ptr[tlen++] = NUL; 1177 else 1178 ptr[tlen++] = p[ni]; 1179 } 1180 read_buf_col += n; 1181 break; 1182 } 1183 else 1184 { 1185 /* Append whole line and new-line. Change NL 1186 * to NUL to reverse the effect done below. */ 1187 for (ni = 0; ni < n; ++ni) 1188 { 1189 if (p[ni] == NL) 1190 ptr[tlen++] = NUL; 1191 else 1192 ptr[tlen++] = p[ni]; 1193 } 1194 ptr[tlen++] = NL; 1195 read_buf_col = 0; 1196 if (++read_buf_lnum > from) 1197 { 1198 /* When the last line didn't have an 1199 * end-of-line don't add it now either. */ 1200 if (!curbuf->b_p_eol) 1201 --tlen; 1202 size = tlen; 1203 break; 1204 } 1205 } 1206 } 1207 } 1208 } 1209 else 1210 { 1211 /* 1212 * Read bytes from the file. 1213 */ 1214 size = vim_read(fd, ptr, size); 1215 } 1216 1217 if (size <= 0) 1218 { 1219 if (size < 0) /* read error */ 1220 error = TRUE; 1221 #ifdef FEAT_MBYTE 1222 else if (conv_restlen > 0) 1223 /* some trailing bytes unconverted */ 1224 conv_error = TRUE; 1225 #endif 1226 } 1227 1228 #ifdef FEAT_CRYPT 1229 /* 1230 * At start of file: Check for magic number of encryption. 1231 */ 1232 if (filesize == 0) 1233 cryptkey = check_for_cryptkey(cryptkey, ptr, &size, 1234 &filesize, newfile); 1235 /* 1236 * Decrypt the read bytes. 1237 */ 1238 if (cryptkey != NULL && size > 0) 1239 for (p = ptr; p < ptr + size; ++p) 1240 ZDECODE(*p); 1241 #endif 1242 } 1243 skip_read = FALSE; 1244 1245 #ifdef FEAT_MBYTE 1246 /* 1247 * At start of file (or after crypt magic number): Check for BOM. 1248 * Also check for a BOM for other Unicode encodings, but not after 1249 * converting with 'charconvert' or when a BOM has already been 1250 * found. 1251 */ 1252 if ((filesize == 0 1253 # ifdef FEAT_CRYPT 1254 || (filesize == CRYPT_MAGIC_LEN && cryptkey != NULL) 1255 # endif 1256 ) 1257 && (fio_flags == FIO_UCSBOM 1258 || (!curbuf->b_p_bomb 1259 && tmpname == NULL 1260 && (*fenc == 'u' || (*fenc == NUL && enc_utf8))))) 1261 { 1262 char_u *ccname; 1263 int blen; 1264 1265 /* no BOM detection in a short file or in binary mode */ 1266 if (size < 2 || curbuf->b_p_bin) 1267 ccname = NULL; 1268 else 1269 ccname = check_for_bom(ptr, size, &blen, 1270 fio_flags == FIO_UCSBOM ? FIO_ALL : get_fio_flags(fenc)); 1271 if (ccname != NULL) 1272 { 1273 /* Remove BOM from the text */ 1274 filesize += blen; 1275 size -= blen; 1276 mch_memmove(ptr, ptr + blen, (size_t)size); 1277 if (newfile) 1278 curbuf->b_p_bomb = TRUE; 1279 } 1280 1281 if (fio_flags == FIO_UCSBOM) 1282 { 1283 if (ccname == NULL) 1284 { 1285 /* No BOM detected: retry with next encoding. */ 1286 advance_fenc = TRUE; 1287 } 1288 else 1289 { 1290 /* BOM detected: set "fenc" and jump back */ 1291 if (fenc_alloced) 1292 vim_free(fenc); 1293 fenc = ccname; 1294 fenc_alloced = FALSE; 1295 } 1296 /* retry reading without getting new bytes or rewinding */ 1297 skip_read = TRUE; 1298 goto retry; 1299 } 1300 } 1301 #endif 1302 /* 1303 * Break here for a read error or end-of-file. 1304 */ 1305 if (size <= 0) 1306 break; 1307 1308 #ifdef FEAT_MBYTE 1309 1310 /* Include not converted bytes. */ 1311 ptr -= conv_restlen; 1312 size += conv_restlen; 1313 conv_restlen = 0; 1314 1315 # ifdef USE_ICONV 1316 if (iconv_fd != (iconv_t)-1) 1317 { 1318 /* 1319 * Attempt conversion of the read bytes to 'encoding' using 1320 * iconv(). 1321 */ 1322 const char *fromp; 1323 char *top; 1324 size_t from_size; 1325 size_t to_size; 1326 1327 fromp = (char *)ptr; 1328 from_size = size; 1329 ptr += size; 1330 top = (char *)ptr; 1331 to_size = real_size - size; 1332 1333 /* 1334 * If there is conversion error or not enough room try using 1335 * another conversion. 1336 */ 1337 if ((iconv(iconv_fd, (void *)&fromp, &from_size, &top, &to_size) 1338 == (size_t)-1 && ICONV_ERRNO != ICONV_EINVAL) 1339 || from_size > CONV_RESTLEN) 1340 goto rewind_retry; 1341 1342 if (from_size > 0) 1343 { 1344 /* Some remaining characters, keep them for the next 1345 * round. */ 1346 mch_memmove(conv_rest, (char_u *)fromp, from_size); 1347 conv_restlen = (int)from_size; 1348 } 1349 1350 /* move the linerest to before the converted characters */ 1351 line_start = ptr - linerest; 1352 mch_memmove(line_start, buffer, (size_t)linerest); 1353 size = (long)((char_u *)top - ptr); 1354 } 1355 # endif 1356 1357 # ifdef WIN3264 1358 if (fio_flags & FIO_CODEPAGE) 1359 { 1360 /* 1361 * Conversion from an MS-Windows codepage or UTF-8 to UTF-8 or 1362 * a codepage, using standard MS-Windows functions. 1363 * 1. find out how many ucs-2 characters there are. 1364 * 2. convert from 'fileencoding' to ucs-2 1365 * 3. convert from ucs-2 to 'encoding' 1366 */ 1367 char_u *ucsp; 1368 size_t from_size = size; 1369 int needed; 1370 char_u *p; 1371 int u8c; 1372 1373 /* 1374 * 1. find out how many ucs-2 characters there are. 1375 */ 1376 # ifdef CP_UTF8 /* VC 4.1 doesn't define CP_UTF8 */ 1377 if (FIO_GET_CP(fio_flags) == CP_UTF8) 1378 { 1379 int l, flen; 1380 1381 /* Handle CP_UTF8 ourselves to be able to handle trailing 1382 * bytes properly. First find out the number of 1383 * characters and check for trailing bytes. */ 1384 needed = 0; 1385 p = ptr; 1386 for (flen = from_size; flen > 0; flen -= l) 1387 { 1388 l = utf_ptr2len_check_len(p, flen); 1389 if (l > flen) /* incomplete char */ 1390 { 1391 if (l > CONV_RESTLEN) 1392 /* weird overlong byte sequence */ 1393 goto rewind_retry; 1394 mch_memmove(conv_rest, p, flen); 1395 conv_restlen = flen; 1396 from_size -= flen; 1397 break; 1398 } 1399 if (l == 1 && *p >= 0x80) /* illegal byte */ 1400 goto rewind_retry; 1401 ++needed; 1402 p += l; 1403 } 1404 } 1405 else 1406 # endif 1407 { 1408 /* We can't tell if the last byte of an MBCS string is 1409 * valid and MultiByteToWideChar() returns zero if it 1410 * isn't. Try the whole string, and if that fails, bump 1411 * the last byte into conv_rest and try again. */ 1412 needed = MultiByteToWideChar(FIO_GET_CP(fio_flags), 1413 MB_ERR_INVALID_CHARS, (LPCSTR)ptr, from_size, 1414 NULL, 0); 1415 if (needed == 0) 1416 { 1417 conv_rest[0] = ptr[from_size - 1]; 1418 conv_restlen = 1; 1419 --from_size; 1420 needed = MultiByteToWideChar(FIO_GET_CP(fio_flags), 1421 MB_ERR_INVALID_CHARS, (LPCSTR)ptr, from_size, 1422 NULL, 0); 1423 } 1424 1425 /* If there really is a conversion error, try using another 1426 * conversion. */ 1427 if (needed == 0) 1428 goto rewind_retry; 1429 } 1430 1431 /* 1432 * 2. convert from 'fileencoding' to ucs-2 1433 * 1434 * Put the result of conversion to UCS-2 at the end of the 1435 * buffer, then convert from UCS-2 to UTF-8 or "enc_codepage" 1436 * into the start of the buffer. If there is not enough space 1437 * just fail, there is probably something wrong. 1438 */ 1439 ucsp = ptr + real_size - (needed * sizeof(WCHAR)); 1440 if (ucsp < ptr + size) 1441 goto rewind_retry; 1442 1443 # ifdef CP_UTF8 /* VC 4.1 doesn't define CP_UTF8 */ 1444 if (FIO_GET_CP(fio_flags) == CP_UTF8) 1445 { 1446 int l, flen; 1447 1448 /* Convert from utf-8 to ucs-2. */ 1449 needed = 0; 1450 p = ptr; 1451 for (flen = from_size; flen > 0; flen -= l) 1452 { 1453 l = utf_ptr2len_check_len(p, flen); 1454 u8c = utf_ptr2char(p); 1455 ucsp[needed * 2] = (u8c & 0xff); 1456 ucsp[needed * 2 + 1] = (u8c >> 8); 1457 ++needed; 1458 p += l; 1459 } 1460 } 1461 else 1462 # endif 1463 needed = MultiByteToWideChar(FIO_GET_CP(fio_flags), 1464 MB_ERR_INVALID_CHARS, (LPCSTR)ptr, 1465 from_size, (LPWSTR)ucsp, needed); 1466 1467 /* 1468 * 3. convert from ucs-2 to 'encoding' 1469 */ 1470 if (enc_utf8) 1471 { 1472 /* From UCS-2 to UTF-8. Cannot fail. */ 1473 p = ptr; 1474 for (; needed > 0; --needed) 1475 { 1476 u8c = *ucsp++; 1477 u8c += (*ucsp++ << 8); 1478 p += utf_char2bytes(u8c, p); 1479 } 1480 size = p - ptr; 1481 } 1482 else 1483 { 1484 BOOL bad = FALSE; 1485 1486 /* From UCS-2 to "enc_codepage". If the conversion uses 1487 * the default character "?", the data doesn't fit in this 1488 * encoding, so fail (unless forced). */ 1489 size = WideCharToMultiByte(enc_codepage, 0, 1490 (LPCWSTR)ucsp, needed, 1491 (LPSTR)ptr, real_size, "?", &bad); 1492 if (bad && !keep_dest_enc) 1493 goto rewind_retry; 1494 } 1495 } 1496 else 1497 # endif 1498 # ifdef MACOS_X 1499 if (fio_flags & FIO_MACROMAN) 1500 { 1501 extern int macroman2enc __ARGS((char_u *ptr, long *sizep, long 1502 real_size)); 1503 /* 1504 * Conversion from Apple MacRoman char encoding to UTF-8 or 1505 * latin1. This is in os_mac_conv.c. 1506 */ 1507 if (macroman2enc(ptr, &size, real_size) == FAIL) 1508 goto rewind_retry; 1509 } 1510 else 1511 # endif 1512 if (fio_flags != 0) 1513 { 1514 int u8c; 1515 char_u *dest; 1516 char_u *tail = NULL; 1517 1518 /* 1519 * "enc_utf8" set: Convert Unicode or Latin1 to UTF-8. 1520 * "enc_utf8" not set: Convert Unicode to Latin1. 1521 * Go from end to start through the buffer, because the number 1522 * of bytes may increase. 1523 * "dest" points to after where the UTF-8 bytes go, "p" points 1524 * to after the next character to convert. 1525 */ 1526 dest = ptr + real_size; 1527 if (fio_flags == FIO_LATIN1 || fio_flags == FIO_UTF8) 1528 { 1529 p = ptr + size; 1530 if (fio_flags == FIO_UTF8) 1531 { 1532 /* Check for a trailing incomplete UTF-8 sequence */ 1533 tail = ptr + size - 1; 1534 while (tail > ptr && (*tail & 0xc0) == 0x80) 1535 --tail; 1536 if (tail + utf_byte2len(*tail) <= ptr + size) 1537 tail = NULL; 1538 else 1539 p = tail; 1540 } 1541 } 1542 else if (fio_flags & (FIO_UCS2 | FIO_UTF16)) 1543 { 1544 /* Check for a trailing byte */ 1545 p = ptr + (size & ~1); 1546 if (size & 1) 1547 tail = p; 1548 if ((fio_flags & FIO_UTF16) && p > ptr) 1549 { 1550 /* Check for a trailing leading word */ 1551 if (fio_flags & FIO_ENDIAN_L) 1552 { 1553 u8c = (*--p << 8); 1554 u8c += *--p; 1555 } 1556 else 1557 { 1558 u8c = *--p; 1559 u8c += (*--p << 8); 1560 } 1561 if (u8c >= 0xd800 && u8c <= 0xdbff) 1562 tail = p; 1563 else 1564 p += 2; 1565 } 1566 } 1567 else /* FIO_UCS4 */ 1568 { 1569 /* Check for trailing 1, 2 or 3 bytes */ 1570 p = ptr + (size & ~3); 1571 if (size & 3) 1572 tail = p; 1573 } 1574 1575 /* If there is a trailing incomplete sequence move it to 1576 * conv_rest[]. */ 1577 if (tail != NULL) 1578 { 1579 conv_restlen = (int)((ptr + size) - tail); 1580 mch_memmove(conv_rest, (char_u *)tail, conv_restlen); 1581 size -= conv_restlen; 1582 } 1583 1584 1585 while (p > ptr) 1586 { 1587 if (fio_flags & FIO_LATIN1) 1588 u8c = *--p; 1589 else if (fio_flags & (FIO_UCS2 | FIO_UTF16)) 1590 { 1591 if (fio_flags & FIO_ENDIAN_L) 1592 { 1593 u8c = (*--p << 8); 1594 u8c += *--p; 1595 } 1596 else 1597 { 1598 u8c = *--p; 1599 u8c += (*--p << 8); 1600 } 1601 if ((fio_flags & FIO_UTF16) 1602 && u8c >= 0xdc00 && u8c <= 0xdfff) 1603 { 1604 int u16c; 1605 1606 if (p == ptr) 1607 { 1608 /* Missing leading word. */ 1609 if (can_retry) 1610 goto rewind_retry; 1611 conv_error = TRUE; 1612 } 1613 1614 /* found second word of double-word, get the first 1615 * word and compute the resulting character */ 1616 if (fio_flags & FIO_ENDIAN_L) 1617 { 1618 u16c = (*--p << 8); 1619 u16c += *--p; 1620 } 1621 else 1622 { 1623 u16c = *--p; 1624 u16c += (*--p << 8); 1625 } 1626 /* Check if the word is indeed a leading word. */ 1627 if (u16c < 0xd800 || u16c > 0xdbff) 1628 { 1629 if (can_retry) 1630 goto rewind_retry; 1631 conv_error = TRUE; 1632 } 1633 u8c = 0x10000 + ((u16c & 0x3ff) << 10) 1634 + (u8c & 0x3ff); 1635 } 1636 } 1637 else if (fio_flags & FIO_UCS4) 1638 { 1639 if (fio_flags & FIO_ENDIAN_L) 1640 { 1641 u8c = (*--p << 24); 1642 u8c += (*--p << 16); 1643 u8c += (*--p << 8); 1644 u8c += *--p; 1645 } 1646 else /* big endian */ 1647 { 1648 u8c = *--p; 1649 u8c += (*--p << 8); 1650 u8c += (*--p << 16); 1651 u8c += (*--p << 24); 1652 } 1653 } 1654 else /* UTF-8 */ 1655 { 1656 if (*--p < 0x80) 1657 u8c = *p; 1658 else 1659 { 1660 len = utf_head_off(ptr, p); 1661 if (len == 0) 1662 { 1663 /* Not a valid UTF-8 character, retry with 1664 * another fenc when possible, otherwise just 1665 * report the error. */ 1666 if (can_retry) 1667 goto rewind_retry; 1668 conv_error = TRUE; 1669 } 1670 p -= len; 1671 u8c = utf_ptr2char(p); 1672 } 1673 } 1674 if (enc_utf8) /* produce UTF-8 */ 1675 { 1676 dest -= utf_char2len(u8c); 1677 (void)utf_char2bytes(u8c, dest); 1678 } 1679 else /* produce Latin1 */ 1680 { 1681 --dest; 1682 if (u8c >= 0x100) 1683 { 1684 /* character doesn't fit in latin1, retry with 1685 * another fenc when possible, otherwise just 1686 * report the error. */ 1687 if (can_retry && !keep_dest_enc) 1688 goto rewind_retry; 1689 *dest = 0xBF; 1690 conv_error = TRUE; 1691 } 1692 else 1693 *dest = u8c; 1694 } 1695 } 1696 1697 /* move the linerest to before the converted characters */ 1698 line_start = dest - linerest; 1699 mch_memmove(line_start, buffer, (size_t)linerest); 1700 size = (long)((ptr + real_size) - dest); 1701 ptr = dest; 1702 } 1703 else if (enc_utf8 && !conv_error && !curbuf->b_p_bin) 1704 { 1705 /* Reading UTF-8: Check if the bytes are valid UTF-8. 1706 * Need to start before "ptr" when part of the character was 1707 * read in the previous read() call. */ 1708 for (p = ptr - utf_head_off(buffer, ptr); p < ptr + size; ++p) 1709 { 1710 if (*p >= 0x80) 1711 { 1712 len = utf_ptr2len_check(p); 1713 /* A length of 1 means it's an illegal byte. Accept 1714 * an incomplete character at the end though, the next 1715 * read() will get the next bytes, we'll check it 1716 * then. */ 1717 if (len == 1) 1718 { 1719 p += utf_byte2len(*p) - 1; 1720 break; 1721 } 1722 p += len - 1; 1723 } 1724 } 1725 if (p < ptr + size) 1726 { 1727 /* Detected a UTF-8 error. */ 1728 if (can_retry) 1729 { 1730 rewind_retry: 1731 /* Retry reading with another conversion. */ 1732 # if defined(FEAT_EVAL) && defined(USE_ICONV) 1733 if (*p_ccv != NUL && iconv_fd != (iconv_t)-1) 1734 /* iconv() failed, try 'charconvert' */ 1735 did_iconv = TRUE; 1736 else 1737 # endif 1738 /* use next item from 'fileencodings' */ 1739 advance_fenc = TRUE; 1740 file_rewind = TRUE; 1741 goto retry; 1742 } 1743 1744 /* There is no alternative fenc, just report the error. */ 1745 # ifdef USE_ICONV 1746 if (iconv_fd != (iconv_t)-1) 1747 conv_error = TRUE; 1748 else 1749 # endif 1750 { 1751 char_u *s; 1752 1753 /* Estimate the line number. */ 1754 illegal_byte = curbuf->b_ml.ml_line_count - linecnt + 1; 1755 for (s = ptr; s < p; ++s) 1756 if (*s == '\n') 1757 ++illegal_byte; 1758 } 1759 } 1760 } 1761 #endif 1762 1763 /* count the number of characters (after conversion!) */ 1764 filesize += size; 1765 1766 /* 1767 * when reading the first part of a file: guess EOL type 1768 */ 1769 if (fileformat == EOL_UNKNOWN) 1770 { 1771 /* First try finding a NL, for Dos and Unix */ 1772 if (try_dos || try_unix) 1773 { 1774 for (p = ptr; p < ptr + size; ++p) 1775 { 1776 if (*p == NL) 1777 { 1778 if (!try_unix 1779 || (try_dos && p > ptr && p[-1] == CAR)) 1780 fileformat = EOL_DOS; 1781 else 1782 fileformat = EOL_UNIX; 1783 break; 1784 } 1785 } 1786 1787 /* Don't give in to EOL_UNIX if EOL_MAC is more likely */ 1788 if (fileformat == EOL_UNIX && try_mac) 1789 { 1790 /* Need to reset the counters when retrying fenc. */ 1791 try_mac = 1; 1792 try_unix = 1; 1793 for (; p >= ptr && *p != CAR; p--) 1794 ; 1795 if (p >= ptr) 1796 { 1797 for (p = ptr; p < ptr + size; ++p) 1798 { 1799 if (*p == NL) 1800 try_unix++; 1801 else if (*p == CAR) 1802 try_mac++; 1803 } 1804 if (try_mac > try_unix) 1805 fileformat = EOL_MAC; 1806 } 1807 } 1808 } 1809 1810 /* No NL found: may use Mac format */ 1811 if (fileformat == EOL_UNKNOWN && try_mac) 1812 fileformat = EOL_MAC; 1813 1814 /* Still nothing found? Use first format in 'ffs' */ 1815 if (fileformat == EOL_UNKNOWN) 1816 fileformat = default_fileformat(); 1817 1818 /* if editing a new file: may set p_tx and p_ff */ 1819 if (newfile) 1820 set_fileformat(fileformat, OPT_LOCAL); 1821 } 1822 } 1823 1824 /* 1825 * This loop is executed once for every character read. 1826 * Keep it fast! 1827 */ 1828 if (fileformat == EOL_MAC) 1829 { 1830 --ptr; 1831 while (++ptr, --size >= 0) 1832 { 1833 /* catch most common case first */ 1834 if ((c = *ptr) != NUL && c != CAR && c != NL) 1835 continue; 1836 if (c == NUL) 1837 *ptr = NL; /* NULs are replaced by newlines! */ 1838 else if (c == NL) 1839 *ptr = CAR; /* NLs are replaced by CRs! */ 1840 else 1841 { 1842 if (skip_count == 0) 1843 { 1844 *ptr = NUL; /* end of line */ 1845 len = (colnr_T) (ptr - line_start + 1); 1846 if (ml_append(lnum, line_start, len, newfile) == FAIL) 1847 { 1848 error = TRUE; 1849 break; 1850 } 1851 ++lnum; 1852 if (--read_count == 0) 1853 { 1854 error = TRUE; /* break loop */ 1855 line_start = ptr; /* nothing left to write */ 1856 break; 1857 } 1858 } 1859 else 1860 --skip_count; 1861 line_start = ptr + 1; 1862 } 1863 } 1864 } 1865 else 1866 { 1867 --ptr; 1868 while (++ptr, --size >= 0) 1869 { 1870 if ((c = *ptr) != NUL && c != NL) /* catch most common case */ 1871 continue; 1872 if (c == NUL) 1873 *ptr = NL; /* NULs are replaced by newlines! */ 1874 else 1875 { 1876 if (skip_count == 0) 1877 { 1878 *ptr = NUL; /* end of line */ 1879 len = (colnr_T)(ptr - line_start + 1); 1880 if (fileformat == EOL_DOS) 1881 { 1882 if (ptr[-1] == CAR) /* remove CR */ 1883 { 1884 ptr[-1] = NUL; 1885 --len; 1886 } 1887 /* 1888 * Reading in Dos format, but no CR-LF found! 1889 * When 'fileformats' includes "unix", delete all 1890 * the lines read so far and start all over again. 1891 * Otherwise give an error message later. 1892 */ 1893 else if (ff_error != EOL_DOS) 1894 { 1895 if ( try_unix 1896 && !read_stdin 1897 && (read_buffer 1898 || lseek(fd, (off_t)0L, SEEK_SET) == 0)) 1899 { 1900 fileformat = EOL_UNIX; 1901 if (newfile) 1902 set_fileformat(EOL_UNIX, OPT_LOCAL); 1903 file_rewind = TRUE; 1904 keep_fileformat = TRUE; 1905 goto retry; 1906 } 1907 ff_error = EOL_DOS; 1908 } 1909 } 1910 if (ml_append(lnum, line_start, len, newfile) == FAIL) 1911 { 1912 error = TRUE; 1913 break; 1914 } 1915 ++lnum; 1916 if (--read_count == 0) 1917 { 1918 error = TRUE; /* break loop */ 1919 line_start = ptr; /* nothing left to write */ 1920 break; 1921 } 1922 } 1923 else 1924 --skip_count; 1925 line_start = ptr + 1; 1926 } 1927 } 1928 } 1929 linerest = (long)(ptr - line_start); 1930 ui_breakcheck(); 1931 } 1932 1933 failed: 1934 /* not an error, max. number of lines reached */ 1935 if (error && read_count == 0) 1936 error = FALSE; 1937 1938 /* 1939 * If we get EOF in the middle of a line, note the fact and 1940 * complete the line ourselves. 1941 * In Dos format ignore a trailing CTRL-Z, unless 'binary' set. 1942 */ 1943 if (!error 1944 && !got_int 1945 && linerest != 0 1946 && !(!curbuf->b_p_bin 1947 && fileformat == EOL_DOS 1948 && *line_start == Ctrl_Z 1949 && ptr == line_start + 1)) 1950 { 1951 if (newfile) /* remember for when writing */ 1952 curbuf->b_p_eol = FALSE; 1953 *ptr = NUL; 1954 if (ml_append(lnum, line_start, 1955 (colnr_T)(ptr - line_start + 1), newfile) == FAIL) 1956 error = TRUE; 1957 else 1958 read_no_eol_lnum = ++lnum; 1959 } 1960 1961 if (newfile) 1962 save_file_ff(curbuf); /* remember the current file format */ 1963 1964 #ifdef FEAT_CRYPT 1965 if (cryptkey != curbuf->b_p_key) 1966 vim_free(cryptkey); 1967 #endif 1968 1969 #ifdef FEAT_MBYTE 1970 /* If editing a new file: set 'fenc' for the current buffer. */ 1971 if (newfile) 1972 set_string_option_direct((char_u *)"fenc", -1, fenc, 1973 OPT_FREE|OPT_LOCAL); 1974 if (fenc_alloced) 1975 vim_free(fenc); 1976 # ifdef USE_ICONV 1977 if (iconv_fd != (iconv_t)-1) 1978 { 1979 iconv_close(iconv_fd); 1980 iconv_fd = (iconv_t)-1; 1981 } 1982 # endif 1983 #endif 1984 1985 if (!read_buffer && !read_stdin) 1986 close(fd); /* errors are ignored */ 1987 vim_free(buffer); 1988 1989 #ifdef HAVE_DUP 1990 if (read_stdin) 1991 { 1992 /* Use stderr for stdin, makes shell commands work. */ 1993 close(0); 1994 dup(2); 1995 } 1996 #endif 1997 1998 #ifdef FEAT_MBYTE 1999 if (tmpname != NULL) 2000 { 2001 mch_remove(tmpname); /* delete converted file */ 2002 vim_free(tmpname); 2003 } 2004 #endif 2005 --no_wait_return; /* may wait for return now */ 2006 2007 /* 2008 * In recovery mode everything but autocommands is skipped. 2009 */ 2010 if (!recoverymode) 2011 { 2012 /* need to delete the last line, which comes from the empty buffer */ 2013 if (newfile && wasempty && !(curbuf->b_ml.ml_flags & ML_EMPTY)) 2014 { 2015 #ifdef FEAT_NETBEANS_INTG 2016 netbeansFireChanges = 0; 2017 #endif 2018 ml_delete(curbuf->b_ml.ml_line_count, FALSE); 2019 #ifdef FEAT_NETBEANS_INTG 2020 netbeansFireChanges = 1; 2021 #endif 2022 --linecnt; 2023 } 2024 linecnt = curbuf->b_ml.ml_line_count - linecnt; 2025 if (filesize == 0) 2026 linecnt = 0; 2027 if (newfile || read_buffer) 2028 redraw_curbuf_later(NOT_VALID); 2029 else if (linecnt) /* appended at least one line */ 2030 appended_lines_mark(from, linecnt); 2031 2032 #ifdef FEAT_DIFF 2033 /* After reading the text into the buffer the diff info needs to be 2034 * updated. */ 2035 if ((newfile || read_buffer)) 2036 diff_invalidate(); 2037 #endif 2038 #ifndef ALWAYS_USE_GUI 2039 /* 2040 * If we were reading from the same terminal as where messages go, 2041 * the screen will have been messed up. 2042 * Switch on raw mode now and clear the screen. 2043 */ 2044 if (read_stdin) 2045 { 2046 settmode(TMODE_RAW); /* set to raw mode */ 2047 starttermcap(); 2048 screenclear(); 2049 } 2050 #endif 2051 2052 if (got_int) 2053 { 2054 if (!(flags & READ_DUMMY)) 2055 { 2056 filemess(curbuf, sfname, (char_u *)_(e_interr), 0); 2057 if (newfile) 2058 curbuf->b_p_ro = TRUE; /* must use "w!" now */ 2059 } 2060 msg_scroll = msg_save; 2061 #ifdef FEAT_VIMINFO 2062 check_marks_read(); 2063 #endif 2064 return OK; /* an interrupt isn't really an error */ 2065 } 2066 2067 if (!filtering && !(flags & READ_DUMMY)) 2068 { 2069 msg_add_fname(curbuf, sfname); /* fname in IObuff with quotes */ 2070 c = FALSE; 2071 2072 #ifdef UNIX 2073 # ifdef S_ISFIFO 2074 if (S_ISFIFO(perm)) /* fifo or socket */ 2075 { 2076 STRCAT(IObuff, _("[fifo/socket]")); 2077 c = TRUE; 2078 } 2079 # else 2080 # ifdef S_IFIFO 2081 if ((perm & S_IFMT) == S_IFIFO) /* fifo */ 2082 { 2083 STRCAT(IObuff, _("[fifo]")); 2084 c = TRUE; 2085 } 2086 # endif 2087 # ifdef S_IFSOCK 2088 if ((perm & S_IFMT) == S_IFSOCK) /* or socket */ 2089 { 2090 STRCAT(IObuff, _("[socket]")); 2091 c = TRUE; 2092 } 2093 # endif 2094 # endif 2095 #endif 2096 if (curbuf->b_p_ro) 2097 { 2098 STRCAT(IObuff, shortmess(SHM_RO) ? _("[RO]") : _("[readonly]")); 2099 c = TRUE; 2100 } 2101 if (read_no_eol_lnum) 2102 { 2103 msg_add_eol(); 2104 c = TRUE; 2105 } 2106 if (ff_error == EOL_DOS) 2107 { 2108 STRCAT(IObuff, _("[CR missing]")); 2109 c = TRUE; 2110 } 2111 if (ff_error == EOL_MAC) 2112 { 2113 STRCAT(IObuff, _("[NL found]")); 2114 c = TRUE; 2115 } 2116 if (split) 2117 { 2118 STRCAT(IObuff, _("[long lines split]")); 2119 c = TRUE; 2120 } 2121 #ifdef FEAT_MBYTE 2122 if (notconverted) 2123 { 2124 STRCAT(IObuff, _("[NOT converted]")); 2125 c = TRUE; 2126 } 2127 else if (converted) 2128 { 2129 STRCAT(IObuff, _("[converted]")); 2130 c = TRUE; 2131 } 2132 #endif 2133 #ifdef FEAT_CRYPT 2134 if (cryptkey != NULL) 2135 { 2136 STRCAT(IObuff, _("[crypted]")); 2137 c = TRUE; 2138 } 2139 #endif 2140 #ifdef FEAT_MBYTE 2141 if (conv_error) 2142 { 2143 STRCAT(IObuff, _("[CONVERSION ERROR]")); 2144 c = TRUE; 2145 } 2146 else if (illegal_byte > 0) 2147 { 2148 sprintf((char *)IObuff + STRLEN(IObuff), 2149 _("[ILLEGAL BYTE in line %ld]"), (long)illegal_byte); 2150 c = TRUE; 2151 } 2152 else 2153 #endif 2154 if (error) 2155 { 2156 STRCAT(IObuff, _("[READ ERRORS]")); 2157 c = TRUE; 2158 } 2159 if (msg_add_fileformat(fileformat)) 2160 c = TRUE; 2161 #ifdef FEAT_CRYPT 2162 if (cryptkey != NULL) 2163 msg_add_lines(c, (long)linecnt, filesize - CRYPT_MAGIC_LEN); 2164 else 2165 #endif 2166 msg_add_lines(c, (long)linecnt, filesize); 2167 2168 vim_free(keep_msg); 2169 keep_msg = NULL; 2170 msg_scrolled_ign = TRUE; 2171 #ifdef ALWAYS_USE_GUI 2172 /* Don't show the message when reading stdin, it would end up in a 2173 * message box (which might be shown when exiting!) */ 2174 if (read_stdin || read_buffer) 2175 p = msg_may_trunc(FALSE, IObuff); 2176 else 2177 #endif 2178 p = msg_trunc_attr(IObuff, FALSE, 0); 2179 if (read_stdin || read_buffer || restart_edit != 0 2180 || (msg_scrolled && !need_wait_return)) 2181 { 2182 /* Need to repeat the message after redrawing when: 2183 * - When reading from stdin (the screen will be cleared next). 2184 * - When restart_edit is set (otherwise there will be a delay 2185 * before redrawing). 2186 * - When the screen was scrolled but there is no wait-return 2187 * prompt. */ 2188 set_keep_msg(p); 2189 keep_msg_attr = 0; 2190 } 2191 msg_scrolled_ign = FALSE; 2192 } 2193 2194 /* with errors writing the file requires ":w!" */ 2195 if (newfile && (error 2196 #ifdef FEAT_MBYTE 2197 || conv_error 2198 #endif 2199 )) 2200 curbuf->b_p_ro = TRUE; 2201 2202 u_clearline(); /* cannot use "U" command after adding lines */ 2203 2204 /* 2205 * In Ex mode: cursor at last new line. 2206 * Otherwise: cursor at first new line. 2207 */ 2208 if (exmode_active) 2209 curwin->w_cursor.lnum = from + linecnt; 2210 else 2211 curwin->w_cursor.lnum = from + 1; 2212 check_cursor_lnum(); 2213 beginline(BL_WHITE | BL_FIX); /* on first non-blank */ 2214 2215 /* 2216 * Set '[ and '] marks to the newly read lines. 2217 */ 2218 curbuf->b_op_start.lnum = from + 1; 2219 curbuf->b_op_start.col = 0; 2220 curbuf->b_op_end.lnum = from + linecnt; 2221 curbuf->b_op_end.col = 0; 2222 } 2223 msg_scroll = msg_save; 2224 2225 #ifdef FEAT_VIMINFO 2226 /* 2227 * Get the marks before executing autocommands, so they can be used there. 2228 */ 2229 check_marks_read(); 2230 #endif 2231 2232 #ifdef FEAT_AUTOCMD 2233 /* 2234 * Trick: We remember if the last line of the read didn't have 2235 * an eol for when writing it again. This is required for 2236 * ":autocmd FileReadPost *.gz set bin|'[,']!gunzip" to work. 2237 */ 2238 write_no_eol_lnum = read_no_eol_lnum; 2239 2240 if (!read_stdin && !read_buffer) 2241 { 2242 int m = msg_scroll; 2243 int n = msg_scrolled; 2244 2245 /* Save the fileformat now, otherwise the buffer will be considered 2246 * modified if the format/encoding was automatically detected. */ 2247 if (newfile) 2248 save_file_ff(curbuf); 2249 2250 /* 2251 * The output from the autocommands should not overwrite anything and 2252 * should not be overwritten: Set msg_scroll, restore its value if no 2253 * output was done. 2254 */ 2255 msg_scroll = TRUE; 2256 if (filtering) 2257 apply_autocmds_exarg(EVENT_FILTERREADPOST, NULL, sfname, 2258 FALSE, curbuf, eap); 2259 else if (newfile) 2260 apply_autocmds_exarg(EVENT_BUFREADPOST, NULL, sfname, 2261 FALSE, curbuf, eap); 2262 else 2263 apply_autocmds_exarg(EVENT_FILEREADPOST, sfname, sfname, 2264 FALSE, NULL, eap); 2265 if (msg_scrolled == n) 2266 msg_scroll = m; 2267 #ifdef FEAT_EVAL 2268 if (aborting()) /* autocmds may abort script processing */ 2269 return FAIL; 2270 #endif 2271 } 2272 #endif 2273 2274 if (recoverymode && error) 2275 return FAIL; 2276 return OK; 2277 } 2278 2279 /* 2280 * Fill "*eap" to force the 'fileencoding' and 'fileformat' to be equal to the 2281 * buffer "buf". Used for calling readfile(). 2282 * Returns OK or FAIL. 2283 */ 2284 int 2285 prep_exarg(eap, buf) 2286 exarg_T *eap; 2287 buf_T *buf; 2288 { 2289 eap->cmd = alloc((unsigned)(STRLEN(buf->b_p_ff) 2290 #ifdef FEAT_MBYTE 2291 + STRLEN(buf->b_p_fenc) 2292 #endif 2293 + 15)); 2294 if (eap->cmd == NULL) 2295 return FAIL; 2296 2297 #ifdef FEAT_MBYTE 2298 sprintf((char *)eap->cmd, "e ++ff=%s ++enc=%s", buf->b_p_ff, buf->b_p_fenc); 2299 eap->force_enc = 14 + (int)STRLEN(buf->b_p_ff); 2300 #else 2301 sprintf((char *)eap->cmd, "e ++ff=%s", buf->b_p_ff); 2302 #endif 2303 eap->force_ff = 7; 2304 return OK; 2305 } 2306 2307 #ifdef FEAT_MBYTE 2308 /* 2309 * Find next fileencoding to use from 'fileencodings'. 2310 * "pp" points to fenc_next. It's advanced to the next item. 2311 * When there are no more items, an empty string is returned and *pp is set to 2312 * NULL. 2313 * When *pp is not set to NULL, the result is in allocated memory. 2314 */ 2315 static char_u * 2316 next_fenc(pp) 2317 char_u **pp; 2318 { 2319 char_u *p; 2320 char_u *r; 2321 2322 if (**pp == NUL) 2323 { 2324 *pp = NULL; 2325 return (char_u *)""; 2326 } 2327 p = vim_strchr(*pp, ','); 2328 if (p == NULL) 2329 { 2330 r = enc_canonize(*pp); 2331 *pp += STRLEN(*pp); 2332 } 2333 else 2334 { 2335 r = vim_strnsave(*pp, (int)(p - *pp)); 2336 *pp = p + 1; 2337 if (r != NULL) 2338 { 2339 p = enc_canonize(r); 2340 vim_free(r); 2341 r = p; 2342 } 2343 } 2344 if (r == NULL) /* out of memory */ 2345 { 2346 r = (char_u *)""; 2347 *pp = NULL; 2348 } 2349 return r; 2350 } 2351 2352 # ifdef FEAT_EVAL 2353 /* 2354 * Convert a file with the 'charconvert' expression. 2355 * This closes the file which is to be read, converts it and opens the 2356 * resulting file for reading. 2357 * Returns name of the resulting converted file (the caller should delete it 2358 * after reading it). 2359 * Returns NULL if the conversion failed ("*fdp" is not set) . 2360 */ 2361 static char_u * 2362 readfile_charconvert(fname, fenc, fdp) 2363 char_u *fname; /* name of input file */ 2364 char_u *fenc; /* converted from */ 2365 int *fdp; /* in/out: file descriptor of file */ 2366 { 2367 char_u *tmpname; 2368 char_u *errmsg = NULL; 2369 2370 tmpname = vim_tempname('r'); 2371 if (tmpname == NULL) 2372 errmsg = (char_u *)_("Can't find temp file for conversion"); 2373 else 2374 { 2375 close(*fdp); /* close the input file, ignore errors */ 2376 *fdp = -1; 2377 if (eval_charconvert(fenc, enc_utf8 ? (char_u *)"utf-8" : p_enc, 2378 fname, tmpname) == FAIL) 2379 errmsg = (char_u *)_("Conversion with 'charconvert' failed"); 2380 if (errmsg == NULL && (*fdp = mch_open((char *)tmpname, 2381 O_RDONLY | O_EXTRA, 0)) < 0) 2382 errmsg = (char_u *)_("can't read output of 'charconvert'"); 2383 } 2384 2385 if (errmsg != NULL) 2386 { 2387 /* Don't use emsg(), it breaks mappings, the retry with 2388 * another type of conversion might still work. */ 2389 MSG(errmsg); 2390 if (tmpname != NULL) 2391 { 2392 mch_remove(tmpname); /* delete converted file */ 2393 vim_free(tmpname); 2394 tmpname = NULL; 2395 } 2396 } 2397 2398 /* If the input file is closed, open it (caller should check for error). */ 2399 if (*fdp < 0) 2400 *fdp = mch_open((char *)fname, O_RDONLY | O_EXTRA, 0); 2401 2402 return tmpname; 2403 } 2404 # endif 2405 2406 #endif 2407 2408 #ifdef FEAT_VIMINFO 2409 /* 2410 * Read marks for the current buffer from the viminfo file, when we support 2411 * buffer marks and the buffer has a name. 2412 */ 2413 static void 2414 check_marks_read() 2415 { 2416 if (!curbuf->b_marks_read && get_viminfo_parameter('\'') > 0 2417 && curbuf->b_ffname != NULL) 2418 read_viminfo(NULL, FALSE, TRUE, FALSE); 2419 2420 /* Always set b_marks_read; needed when 'viminfo' is changed to include 2421 * the ' parameter after opening a buffer. */ 2422 curbuf->b_marks_read = TRUE; 2423 } 2424 #endif 2425 2426 #ifdef FEAT_CRYPT 2427 /* 2428 * Check for magic number used for encryption. 2429 * If found, the magic number is removed from ptr[*sizep] and *sizep and 2430 * *filesizep are updated. 2431 * Return the (new) encryption key, NULL for no encryption. 2432 */ 2433 static char_u * 2434 check_for_cryptkey(cryptkey, ptr, sizep, filesizep, newfile) 2435 char_u *cryptkey; /* previous encryption key or NULL */ 2436 char_u *ptr; /* pointer to read bytes */ 2437 long *sizep; /* length of read bytes */ 2438 long *filesizep; /* nr of bytes used from file */ 2439 int newfile; /* editing a new buffer */ 2440 { 2441 if (*sizep >= CRYPT_MAGIC_LEN 2442 && STRNCMP(ptr, CRYPT_MAGIC, CRYPT_MAGIC_LEN) == 0) 2443 { 2444 if (cryptkey == NULL) 2445 { 2446 if (*curbuf->b_p_key) 2447 cryptkey = curbuf->b_p_key; 2448 else 2449 { 2450 /* When newfile is TRUE, store the typed key 2451 * in the 'key' option and don't free it. */ 2452 cryptkey = get_crypt_key(newfile, FALSE); 2453 /* check if empty key entered */ 2454 if (cryptkey != NULL && *cryptkey == NUL) 2455 { 2456 if (cryptkey != curbuf->b_p_key) 2457 vim_free(cryptkey); 2458 cryptkey = NULL; 2459 } 2460 } 2461 } 2462 2463 if (cryptkey != NULL) 2464 { 2465 crypt_init_keys(cryptkey); 2466 2467 /* Remove magic number from the text */ 2468 *filesizep += CRYPT_MAGIC_LEN; 2469 *sizep -= CRYPT_MAGIC_LEN; 2470 mch_memmove(ptr, ptr + CRYPT_MAGIC_LEN, (size_t)*sizep); 2471 } 2472 } 2473 /* When starting to edit a new file which does not have 2474 * encryption, clear the 'key' option, except when 2475 * starting up (called with -x argument) */ 2476 else if (newfile && *curbuf->b_p_key && !starting) 2477 set_option_value((char_u *)"key", 0L, (char_u *)"", OPT_LOCAL); 2478 2479 return cryptkey; 2480 } 2481 #endif 2482 2483 #ifdef UNIX 2484 static void 2485 set_file_time(fname, atime, mtime) 2486 char_u *fname; 2487 time_t atime; /* access time */ 2488 time_t mtime; /* modification time */ 2489 { 2490 # if defined(HAVE_UTIME) && defined(HAVE_UTIME_H) 2491 struct utimbuf buf; 2492 2493 buf.actime = atime; 2494 buf.modtime = mtime; 2495 (void)utime((char *)fname, &buf); 2496 # else 2497 # if defined(HAVE_UTIMES) 2498 struct timeval tvp[2]; 2499 2500 tvp[0].tv_sec = atime; 2501 tvp[0].tv_usec = 0; 2502 tvp[1].tv_sec = mtime; 2503 tvp[1].tv_usec = 0; 2504 # ifdef NeXT 2505 (void)utimes((char *)fname, tvp); 2506 # else 2507 (void)utimes((char *)fname, (const struct timeval *)&tvp); 2508 # endif 2509 # endif 2510 # endif 2511 } 2512 #endif /* UNIX */ 2513 2514 /* 2515 * buf_write() - write to file 'fname' lines 'start' through 'end' 2516 * 2517 * We do our own buffering here because fwrite() is so slow. 2518 * 2519 * If forceit is true, we don't care for errors when attempting backups (jw). 2520 * In case of an error everything possible is done to restore the original file. 2521 * But when forceit is TRUE, we risk loosing it. 2522 * When reset_changed is TRUE and start == 1 and end == 2523 * curbuf->b_ml.ml_line_count, reset curbuf->b_changed. 2524 * 2525 * This function must NOT use NameBuff (because it's called by autowrite()). 2526 * 2527 * return FAIL for failure, OK otherwise 2528 */ 2529 int 2530 buf_write(buf, fname, sfname, start, end, eap, append, forceit, 2531 reset_changed, filtering) 2532 buf_T *buf; 2533 char_u *fname; 2534 char_u *sfname; 2535 linenr_T start, end; 2536 exarg_T *eap; /* for forced 'ff' and 'fenc', can be 2537 NULL! */ 2538 int append; 2539 int forceit; 2540 int reset_changed; 2541 int filtering; 2542 { 2543 int fd; 2544 char_u *backup = NULL; 2545 int backup_copy = FALSE; /* copy the original file? */ 2546 int dobackup; 2547 char_u *ffname; 2548 char_u *wfname = NULL; /* name of file to write to */ 2549 char_u *s; 2550 char_u *ptr; 2551 char_u c; 2552 int len; 2553 linenr_T lnum; 2554 long nchars; 2555 char_u *errmsg = NULL; 2556 char_u *errnum = NULL; 2557 char_u *buffer; 2558 char_u smallbuf[SMBUFSIZE]; 2559 char_u *backup_ext; 2560 int bufsize; 2561 long perm; /* file permissions */ 2562 int retval = OK; 2563 int newfile = FALSE; /* TRUE if file doesn't exist yet */ 2564 int msg_save = msg_scroll; 2565 int overwriting; /* TRUE if writing over original */ 2566 int no_eol = FALSE; /* no end-of-line written */ 2567 int device = FALSE; /* writing to a device */ 2568 struct stat st_old; 2569 int prev_got_int = got_int; 2570 int file_readonly = FALSE; /* overwritten file is read-only */ 2571 static char *err_readonly = "is read-only (cannot override: \"W\" in 'cpoptions')"; 2572 #if defined(UNIX) || defined(__EMX__XX) /*XXX fix me sometime? */ 2573 int made_writable = FALSE; /* 'w' bit has been set */ 2574 #endif 2575 /* writing everything */ 2576 int whole = (start == 1 && end == buf->b_ml.ml_line_count); 2577 #ifdef FEAT_AUTOCMD 2578 linenr_T old_line_count = buf->b_ml.ml_line_count; 2579 #endif 2580 int attr; 2581 int fileformat; 2582 int write_bin; 2583 struct bw_info write_info; /* info for buf_write_bytes() */ 2584 #ifdef FEAT_MBYTE 2585 int converted = FALSE; 2586 int notconverted = FALSE; 2587 char_u *fenc; /* effective 'fileencoding' */ 2588 char_u *fenc_tofree = NULL; /* allocated "fenc" */ 2589 #endif 2590 #ifdef HAS_BW_FLAGS 2591 int wb_flags = 0; 2592 #endif 2593 #ifdef HAVE_ACL 2594 vim_acl_T acl = NULL; /* ACL copied from original file to 2595 backup or new file */ 2596 #endif 2597 2598 if (fname == NULL || *fname == NUL) /* safety check */ 2599 return FAIL; 2600 2601 /* 2602 * Disallow writing from .exrc and .vimrc in current directory for 2603 * security reasons. 2604 */ 2605 if (check_secure()) 2606 return FAIL; 2607 2608 /* Avoid a crash for a long name. */ 2609 if (STRLEN(fname) >= MAXPATHL) 2610 { 2611 EMSG(_(e_longname)); 2612 return FAIL; 2613 } 2614 2615 #ifdef FEAT_MBYTE 2616 /* must init bw_conv_buf and bw_iconv_fd before jumping to "fail" */ 2617 write_info.bw_conv_buf = NULL; 2618 write_info.bw_conv_error = FALSE; 2619 write_info.bw_restlen = 0; 2620 # ifdef USE_ICONV 2621 write_info.bw_iconv_fd = (iconv_t)-1; 2622 # endif 2623 #endif 2624 2625 /* 2626 * If there is no file name yet, use the one for the written file. 2627 * BF_NOTEDITED is set to reflect this (in case the write fails). 2628 * Don't do this when the write is for a filter command. 2629 * Only do this when 'cpoptions' contains the 'f' flag. 2630 */ 2631 if (reset_changed 2632 && whole 2633 && buf == curbuf 2634 && curbuf->b_ffname == NULL 2635 && !filtering 2636 && vim_strchr(p_cpo, CPO_FNAMEW) != NULL) 2637 { 2638 #ifdef FEAT_AUTOCMD 2639 /* It's like the unnamed buffer is deleted.... */ 2640 if (curbuf->b_p_bl) 2641 apply_autocmds(EVENT_BUFDELETE, NULL, NULL, FALSE, curbuf); 2642 apply_autocmds(EVENT_BUFWIPEOUT, NULL, NULL, FALSE, curbuf); 2643 #ifdef FEAT_EVAL 2644 if (aborting()) /* autocmds may abort script processing */ 2645 return FAIL; 2646 #endif 2647 #endif 2648 if (setfname(curbuf, fname, sfname, FALSE) == OK) 2649 curbuf->b_flags |= BF_NOTEDITED; 2650 #ifdef FEAT_AUTOCMD 2651 /* ....and a new named one is created */ 2652 apply_autocmds(EVENT_BUFNEW, NULL, NULL, FALSE, curbuf); 2653 if (curbuf->b_p_bl) 2654 apply_autocmds(EVENT_BUFADD, NULL, NULL, FALSE, curbuf); 2655 #endif 2656 } 2657 2658 if (sfname == NULL) 2659 sfname = fname; 2660 /* 2661 * For Unix: Use the short file name whenever possible. 2662 * Avoids problems with networks and when directory names are changed. 2663 * Don't do this for MS-DOS, a "cd" in a sub-shell may have moved us to 2664 * another directory, which we don't detect 2665 */ 2666 ffname = fname; /* remember full fname */ 2667 #ifdef UNIX 2668 fname = sfname; 2669 #endif 2670 2671 if (buf->b_ffname != NULL && fnamecmp(ffname, buf->b_ffname) == 0) 2672 overwriting = TRUE; 2673 else 2674 overwriting = FALSE; 2675 2676 if (exiting) 2677 settmode(TMODE_COOK); /* when exiting allow typahead now */ 2678 2679 ++no_wait_return; /* don't wait for return yet */ 2680 2681 /* 2682 * Set '[ and '] marks to the lines to be written. 2683 */ 2684 buf->b_op_start.lnum = start; 2685 buf->b_op_start.col = 0; 2686 buf->b_op_end.lnum = end; 2687 buf->b_op_end.col = 0; 2688 2689 #ifdef FEAT_AUTOCMD 2690 { 2691 aco_save_T aco; 2692 int buf_ffname = FALSE; 2693 int buf_sfname = FALSE; 2694 int buf_fname_f = FALSE; 2695 int buf_fname_s = FALSE; 2696 int did_cmd = FALSE; 2697 int nofile_err = FALSE; 2698 2699 /* 2700 * Apply PRE aucocommands. 2701 * Set curbuf to the buffer to be written. 2702 * Careful: The autocommands may call buf_write() recursively! 2703 */ 2704 if (ffname == buf->b_ffname) 2705 buf_ffname = TRUE; 2706 if (sfname == buf->b_sfname) 2707 buf_sfname = TRUE; 2708 if (fname == buf->b_ffname) 2709 buf_fname_f = TRUE; 2710 if (fname == buf->b_sfname) 2711 buf_fname_s = TRUE; 2712 2713 /* set curwin/curbuf to buf and save a few things */ 2714 aucmd_prepbuf(&aco, buf); 2715 2716 if (append) 2717 { 2718 if (!(did_cmd = apply_autocmds_exarg(EVENT_FILEAPPENDCMD, 2719 sfname, sfname, FALSE, curbuf, eap))) 2720 { 2721 if (overwriting && bt_nofile(curbuf)) 2722 nofile_err = TRUE; 2723 else 2724 apply_autocmds_exarg(EVENT_FILEAPPENDPRE, 2725 sfname, sfname, FALSE, curbuf, eap); 2726 } 2727 } 2728 else if (filtering) 2729 { 2730 apply_autocmds_exarg(EVENT_FILTERWRITEPRE, 2731 NULL, sfname, FALSE, curbuf, eap); 2732 } 2733 else if (reset_changed && whole) 2734 { 2735 if (!(did_cmd = apply_autocmds_exarg(EVENT_BUFWRITECMD, 2736 sfname, sfname, FALSE, curbuf, eap))) 2737 { 2738 if (bt_nofile(curbuf)) 2739 nofile_err = TRUE; 2740 else 2741 apply_autocmds_exarg(EVENT_BUFWRITEPRE, 2742 sfname, sfname, FALSE, curbuf, eap); 2743 } 2744 } 2745 else 2746 { 2747 if (!(did_cmd = apply_autocmds_exarg(EVENT_FILEWRITECMD, 2748 sfname, sfname, FALSE, curbuf, eap))) 2749 { 2750 if (bt_nofile(curbuf)) 2751 nofile_err = TRUE; 2752 else 2753 apply_autocmds_exarg(EVENT_FILEWRITEPRE, 2754 sfname, sfname, FALSE, curbuf, eap); 2755 } 2756 } 2757 2758 /* restore curwin/curbuf and a few other things */ 2759 aucmd_restbuf(&aco); 2760 2761 /* 2762 * In three situations we return here and don't write the file: 2763 * 1. the autocommands deleted or unloaded the buffer. 2764 * 2. The autocommands abort script processing. 2765 * 3. If one of the "Cmd" autocommands was executed. 2766 */ 2767 if (!buf_valid(buf)) 2768 buf = NULL; 2769 if (buf == NULL || buf->b_ml.ml_mfp == NULL 2770 || did_cmd || nofile_err || aborting()) 2771 { 2772 --no_wait_return; 2773 msg_scroll = msg_save; 2774 if (nofile_err) 2775 EMSG(_("E676: No matching autocommands for acwrite buffer")); 2776 2777 if (aborting() || nofile_err) 2778 /* An aborting error, interrupt or exception in the 2779 * autocommands. */ 2780 return FAIL; 2781 if (did_cmd) 2782 { 2783 if (buf == NULL) 2784 /* The buffer was deleted. We assume it was written 2785 * (can't retry anyway). */ 2786 return OK; 2787 if (overwriting) 2788 { 2789 /* Assume the buffer was written, update the timestamp. */ 2790 ml_timestamp(buf); 2791 buf->b_flags &= ~BF_WRITE_MASK; 2792 } 2793 if (reset_changed && buf->b_changed) 2794 /* Buffer still changed, the autocommands didn't work 2795 * properly. */ 2796 return FAIL; 2797 return OK; 2798 } 2799 #ifdef FEAT_EVAL 2800 if (!aborting()) 2801 #endif 2802 EMSG(_("E203: Autocommands deleted or unloaded buffer to be written")); 2803 return FAIL; 2804 } 2805 2806 /* 2807 * The autocommands may have changed the number of lines in the file. 2808 * When writing the whole file, adjust the end. 2809 * When writing part of the file, assume that the autocommands only 2810 * changed the number of lines that are to be written (tricky!). 2811 */ 2812 if (buf->b_ml.ml_line_count != old_line_count) 2813 { 2814 if (whole) /* write all */ 2815 end = buf->b_ml.ml_line_count; 2816 else if (buf->b_ml.ml_line_count > old_line_count) /* more lines */ 2817 end += buf->b_ml.ml_line_count - old_line_count; 2818 else /* less lines */ 2819 { 2820 end -= old_line_count - buf->b_ml.ml_line_count; 2821 if (end < start) 2822 { 2823 --no_wait_return; 2824 msg_scroll = msg_save; 2825 EMSG(_("E204: Autocommand changed number of lines in unexpected way")); 2826 return FAIL; 2827 } 2828 } 2829 } 2830 2831 /* 2832 * The autocommands may have changed the name of the buffer, which may 2833 * be kept in fname, ffname and sfname. 2834 */ 2835 if (buf_ffname) 2836 ffname = buf->b_ffname; 2837 if (buf_sfname) 2838 sfname = buf->b_sfname; 2839 if (buf_fname_f) 2840 fname = buf->b_ffname; 2841 if (buf_fname_s) 2842 fname = buf->b_sfname; 2843 } 2844 #endif 2845 2846 #ifdef FEAT_NETBEANS_INTG 2847 if (usingNetbeans && isNetbeansBuffer(buf)) 2848 { 2849 if (whole) 2850 { 2851 /* 2852 * b_changed can be 0 after an undo, but we still need to write 2853 * the buffer to NetBeans. 2854 */ 2855 if (buf->b_changed || isNetbeansModified(buf)) 2856 { 2857 netbeans_save_buffer(buf); 2858 return retval; 2859 } 2860 else 2861 { 2862 errnum = (char_u *)"E656: "; 2863 errmsg = (char_u *)_("NetBeans dissallows writes of unmodified buffers"); 2864 buffer = NULL; 2865 goto fail; 2866 } 2867 } 2868 else 2869 { 2870 errnum = (char_u *)"E657: "; 2871 errmsg = (char_u *)_("Partial writes disallowed for NetBeans buffers"); 2872 buffer = NULL; 2873 goto fail; 2874 } 2875 } 2876 #endif 2877 2878 if (shortmess(SHM_OVER) && !exiting) 2879 msg_scroll = FALSE; /* overwrite previous file message */ 2880 else 2881 msg_scroll = TRUE; /* don't overwrite previous file message */ 2882 if (!filtering) 2883 filemess(buf, 2884 #ifndef UNIX 2885 sfname, 2886 #else 2887 fname, 2888 #endif 2889 (char_u *)"", 0); /* show that we are busy */ 2890 msg_scroll = FALSE; /* always overwrite the file message now */ 2891 2892 buffer = alloc(BUFSIZE); 2893 if (buffer == NULL) /* can't allocate big buffer, use small 2894 * one (to be able to write when out of 2895 * memory) */ 2896 { 2897 buffer = smallbuf; 2898 bufsize = SMBUFSIZE; 2899 } 2900 else 2901 bufsize = BUFSIZE; 2902 2903 /* 2904 * Get information about original file (if there is one). 2905 */ 2906 #if defined(UNIX) && !defined(ARCHIE) 2907 st_old.st_dev = st_old.st_ino = 0; 2908 perm = -1; 2909 if (mch_stat((char *)fname, &st_old) < 0) 2910 newfile = TRUE; 2911 else 2912 { 2913 perm = st_old.st_mode; 2914 if (!S_ISREG(st_old.st_mode)) /* not a file */ 2915 { 2916 if (S_ISDIR(st_old.st_mode)) 2917 { 2918 errnum = (char_u *)"E502: "; 2919 errmsg = (char_u *)_("is a directory"); 2920 goto fail; 2921 } 2922 if (mch_nodetype(fname) != NODE_WRITABLE) 2923 { 2924 errnum = (char_u *)"E503: "; 2925 errmsg = (char_u *)_("is not a file or writable device"); 2926 goto fail; 2927 } 2928 /* It's a device of some kind (or a fifo) which we can write to 2929 * but for which we can't make a backup. */ 2930 device = TRUE; 2931 newfile = TRUE; 2932 perm = -1; 2933 } 2934 } 2935 #else /* !UNIX */ 2936 /* 2937 * Check for a writable device name. 2938 */ 2939 c = mch_nodetype(fname); 2940 if (c == NODE_OTHER) 2941 { 2942 errnum = (char_u *)"E503: "; 2943 errmsg = (char_u *)_("is not a file or writable device"); 2944 goto fail; 2945 } 2946 if (c == NODE_WRITABLE) 2947 { 2948 device = TRUE; 2949 newfile = TRUE; 2950 perm = -1; 2951 } 2952 else 2953 { 2954 perm = mch_getperm(fname); 2955 if (perm < 0) 2956 newfile = TRUE; 2957 else if (mch_isdir(fname)) 2958 { 2959 errnum = (char_u *)"E502: "; 2960 errmsg = (char_u *)_("is a directory"); 2961 goto fail; 2962 } 2963 if (overwriting) 2964 (void)mch_stat((char *)fname, &st_old); 2965 } 2966 #endif /* !UNIX */ 2967 2968 if (!device && !newfile) 2969 { 2970 /* 2971 * Check if the file is really writable (when renaming the file to 2972 * make a backup we won't discover it later). 2973 */ 2974 file_readonly = ( 2975 # ifdef USE_MCH_ACCESS 2976 # ifdef UNIX 2977 (perm & 0222) == 0 || 2978 # endif 2979 mch_access((char *)fname, W_OK) 2980 # else 2981 (fd = mch_open((char *)fname, O_RDWR | O_EXTRA, 0)) < 0 2982 ? TRUE : (close(fd), FALSE) 2983 # endif 2984 ); 2985 if (!forceit && file_readonly) 2986 { 2987 if (vim_strchr(p_cpo, CPO_FWRITE) != NULL) 2988 { 2989 errnum = (char_u *)"E504: "; 2990 errmsg = (char_u *)_(err_readonly); 2991 } 2992 else 2993 { 2994 errnum = (char_u *)"E505: "; 2995 errmsg = (char_u *)_("is read-only (add ! to override)"); 2996 } 2997 goto fail; 2998 } 2999 3000 /* 3001 * Check if the timestamp hasn't changed since reading the file. 3002 */ 3003 if (overwriting) 3004 { 3005 retval = check_mtime(buf, &st_old); 3006 if (retval == FAIL) 3007 goto fail; 3008 } 3009 } 3010 3011 #ifdef HAVE_ACL 3012 /* 3013 * For systems that support ACL: get the ACL from the original file. 3014 */ 3015 if (!newfile) 3016 acl = mch_get_acl(fname); 3017 #endif 3018 3019 /* 3020 * If 'backupskip' is not empty, don't make a backup for some files. 3021 */ 3022 dobackup = (p_wb || p_bk || *p_pm != NUL); 3023 #ifdef FEAT_WILDIGN 3024 if (dobackup && *p_bsk != NUL && match_file_list(p_bsk, sfname, ffname)) 3025 dobackup = FALSE; 3026 #endif 3027 3028 /* 3029 * Save the value of got_int and reset it. We don't want a previous 3030 * interruption cancel writing, only hitting CTRL-C while writing should 3031 * abort it. 3032 */ 3033 prev_got_int = got_int; 3034 got_int = FALSE; 3035 3036 /* Mark the buffer as 'being saved' to prevent changed buffer warnings */ 3037 buf->b_saving = TRUE; 3038 3039 /* 3040 * If we are not appending or filtering, the file exists, and the 3041 * 'writebackup', 'backup' or 'patchmode' option is set, need a backup. 3042 * When 'patchmode' is set also make a backup when appending. 3043 * 3044 * Do not make any backup, if 'writebackup' and 'backup' are both switched 3045 * off. This helps when editing large files on almost-full disks. 3046 */ 3047 if (!(append && *p_pm == NUL) && !filtering && perm >= 0 && dobackup) 3048 { 3049 #if defined(UNIX) || defined(WIN32) 3050 struct stat st; 3051 #endif 3052 3053 if ((bkc_flags & BKC_YES) || append) /* "yes" */ 3054 backup_copy = TRUE; 3055 #if defined(UNIX) || defined(WIN32) 3056 else if ((bkc_flags & BKC_AUTO)) /* "auto" */ 3057 { 3058 int i; 3059 3060 # ifdef UNIX 3061 /* 3062 * Don't rename the file when: 3063 * - it's a hard link 3064 * - it's a symbolic link 3065 * - we don't have write permission in the directory 3066 * - we can't set the owner/group of the new file 3067 */ 3068 if (st_old.st_nlink > 1 3069 || mch_lstat((char *)fname, &st) < 0 3070 || st.st_dev != st_old.st_dev 3071 || st.st_ino != st_old.st_ino) 3072 backup_copy = TRUE; 3073 else 3074 # endif 3075 { 3076 /* 3077 * Check if we can create a file and set the owner/group to 3078 * the ones from the original file. 3079 * First find a file name that doesn't exist yet (use some 3080 * arbitrary numbers). 3081 */ 3082 STRCPY(IObuff, fname); 3083 for (i = 4913; ; i += 123) 3084 { 3085 sprintf((char *)gettail(IObuff), "%d", i); 3086 if (mch_stat((char *)IObuff, &st) < 0) 3087 break; 3088 } 3089 fd = mch_open((char *)IObuff, O_CREAT|O_WRONLY|O_EXCL, perm); 3090 close(fd); 3091 if (fd < 0) /* can't write in directory */ 3092 backup_copy = TRUE; 3093 else 3094 { 3095 # ifdef UNIX 3096 chown((char *)IObuff, st_old.st_uid, st_old.st_gid); 3097 (void)mch_setperm(IObuff, perm); 3098 if (mch_stat((char *)IObuff, &st) < 0 3099 || st.st_uid != st_old.st_uid 3100 || st.st_gid != st_old.st_gid 3101 || st.st_mode != perm) 3102 backup_copy = TRUE; 3103 # endif 3104 mch_remove(IObuff); 3105 } 3106 } 3107 } 3108 3109 # ifdef UNIX 3110 /* 3111 * Break symlinks and/or hardlinks if we've been asked to. 3112 */ 3113 if ((bkc_flags & BKC_BREAKSYMLINK) || (bkc_flags & BKC_BREAKHARDLINK)) 3114 { 3115 int lstat_res; 3116 3117 lstat_res = mch_lstat((char *)fname, &st); 3118 3119 /* Symlinks. */ 3120 if ((bkc_flags & BKC_BREAKSYMLINK) 3121 && lstat_res == 0 3122 && st.st_ino != st_old.st_ino) 3123 backup_copy = FALSE; 3124 3125 /* Hardlinks. */ 3126 if ((bkc_flags & BKC_BREAKHARDLINK) 3127 && st_old.st_nlink > 1 3128 && (lstat_res != 0 || st.st_ino == st_old.st_ino)) 3129 backup_copy = FALSE; 3130 } 3131 #endif 3132 3133 #endif 3134 3135 /* make sure we have a valid backup extension to use */ 3136 if (*p_bex == NUL) 3137 { 3138 #ifdef RISCOS 3139 backup_ext = (char_u *)"/bak"; 3140 #else 3141 backup_ext = (char_u *)".bak"; 3142 #endif 3143 } 3144 else 3145 backup_ext = p_bex; 3146 3147 if (backup_copy 3148 && (fd = mch_open((char *)fname, O_RDONLY | O_EXTRA, 0)) >= 0) 3149 { 3150 int bfd; 3151 char_u *copybuf, *wp; 3152 int some_error = FALSE; 3153 struct stat st_new; 3154 char_u *dirp; 3155 char_u *rootname; 3156 #ifndef SHORT_FNAME 3157 int did_set_shortname; 3158 #endif 3159 3160 copybuf = alloc(BUFSIZE + 1); 3161 if (copybuf == NULL) 3162 { 3163 some_error = TRUE; /* out of memory */ 3164 goto nobackup; 3165 } 3166 3167 /* 3168 * Try to make the backup in each directory in the 'bdir' option. 3169 * 3170 * Unix semantics has it, that we may have a writable file, 3171 * that cannot be recreated with a simple open(..., O_CREAT, ) e.g: 3172 * - the directory is not writable, 3173 * - the file may be a symbolic link, 3174 * - the file may belong to another user/group, etc. 3175 * 3176 * For these reasons, the existing writable file must be truncated 3177 * and reused. Creation of a backup COPY will be attempted. 3178 */ 3179 dirp = p_bdir; 3180 while (*dirp) 3181 { 3182 #ifdef UNIX 3183 st_new.st_ino = 0; 3184 st_new.st_dev = 0; 3185 st_new.st_gid = 0; 3186 #endif 3187 3188 /* 3189 * Isolate one directory name, using an entry in 'bdir'. 3190 */ 3191 (void)copy_option_part(&dirp, copybuf, BUFSIZE, ","); 3192 rootname = get_file_in_dir(fname, copybuf); 3193 if (rootname == NULL) 3194 { 3195 some_error = TRUE; /* out of memory */ 3196 goto nobackup; 3197 } 3198 3199 #ifndef SHORT_FNAME 3200 did_set_shortname = FALSE; 3201 #endif 3202 3203 /* 3204 * May try twice if 'shortname' not set. 3205 */ 3206 for (;;) 3207 { 3208 /* 3209 * Make backup file name. 3210 */ 3211 backup = buf_modname( 3212 #ifdef SHORT_FNAME 3213 TRUE, 3214 #else 3215 (buf->b_p_sn || buf->b_shortname), 3216 #endif 3217 rootname, backup_ext, FALSE); 3218 if (backup == NULL) 3219 { 3220 vim_free(rootname); 3221 some_error = TRUE; /* out of memory */ 3222 goto nobackup; 3223 } 3224 3225 /* 3226 * Check if backup file already exists. 3227 */ 3228 if (mch_stat((char *)backup, &st_new) >= 0) 3229 { 3230 #ifdef UNIX 3231 /* 3232 * Check if backup file is same as original file. 3233 * May happen when modname() gave the same file back. 3234 * E.g. silly link, or file name-length reached. 3235 * If we don't check here, we either ruin the file 3236 * when copying or erase it after writing. jw. 3237 */ 3238 if (st_new.st_dev == st_old.st_dev 3239 && st_new.st_ino == st_old.st_ino) 3240 { 3241 vim_free(backup); 3242 backup = NULL; /* no backup file to delete */ 3243 # ifndef SHORT_FNAME 3244 /* 3245 * may try again with 'shortname' set 3246 */ 3247 if (!(buf->b_shortname || buf->b_p_sn)) 3248 { 3249 buf->b_shortname = TRUE; 3250 did_set_shortname = TRUE; 3251 continue; 3252 } 3253 /* setting shortname didn't help */ 3254 if (did_set_shortname) 3255 buf->b_shortname = FALSE; 3256 # endif 3257 break; 3258 } 3259 #endif 3260 3261 /* 3262 * If we are not going to keep the backup file, don't 3263 * delete an existing one, try to use another name. 3264 * Change one character, just before the extension. 3265 */ 3266 if (!p_bk) 3267 { 3268 wp = backup + STRLEN(backup) - 1 3269 - STRLEN(backup_ext); 3270 if (wp < backup) /* empty file name ??? */ 3271 wp = backup; 3272 *wp = 'z'; 3273 while (*wp > 'a' 3274 && mch_stat((char *)backup, &st_new) >= 0) 3275 --*wp; 3276 /* They all exist??? Must be something wrong. */ 3277 if (*wp == 'a') 3278 { 3279 vim_free(backup); 3280 backup = NULL; 3281 } 3282 } 3283 } 3284 break; 3285 } 3286 vim_free(rootname); 3287 3288 /* 3289 * Try to create the backup file 3290 */ 3291 if (backup != NULL) 3292 { 3293 /* remove old backup, if present */ 3294 mch_remove(backup); 3295 /* Open with O_EXCL to avoid the file being created while 3296 * we were sleeping (symlink hacker attack?) */ 3297 bfd = mch_open((char *)backup, 3298 O_WRONLY|O_CREAT|O_EXTRA|O_EXCL, 0666); 3299 if (bfd < 0) 3300 { 3301 vim_free(backup); 3302 backup = NULL; 3303 } 3304 else 3305 { 3306 /* set file protection same as original file, but 3307 * strip s-bit */ 3308 (void)mch_setperm(backup, perm & 0777); 3309 3310 #ifdef UNIX 3311 /* 3312 * Try to set the group of the backup same as the 3313 * original file. If this fails, set the protection 3314 * bits for the group same as the protection bits for 3315 * others. 3316 */ 3317 if (st_new.st_gid != st_old.st_gid && 3318 # ifdef HAVE_FCHOWN /* sequent-ptx lacks fchown() */ 3319 fchown(bfd, (uid_t)-1, st_old.st_gid) != 0 3320 # else 3321 chown((char *)backup, (uid_t)-1, st_old.st_gid) != 0 3322 # endif 3323 ) 3324 mch_setperm(backup, 3325 (perm & 0707) | ((perm & 07) << 3)); 3326 #endif 3327 3328 /* 3329 * copy the file. 3330 */ 3331 write_info.bw_fd = bfd; 3332 write_info.bw_buf = copybuf; 3333 #ifdef HAS_BW_FLAGS 3334 write_info.bw_flags = FIO_NOCONVERT; 3335 #endif 3336 while ((write_info.bw_len = vim_read(fd, copybuf, 3337 BUFSIZE)) > 0) 3338 { 3339 if (buf_write_bytes(&write_info) == FAIL) 3340 { 3341 errmsg = (char_u *)_("E506: Can't write to backup file (add ! to override)"); 3342 break; 3343 } 3344 ui_breakcheck(); 3345 if (got_int) 3346 { 3347 errmsg = (char_u *)_(e_interr); 3348 break; 3349 } 3350 } 3351 3352 if (close(bfd) < 0 && errmsg == NULL) 3353 errmsg = (char_u *)_("E507: Close error for backup file (add ! to override)"); 3354 if (write_info.bw_len < 0) 3355 errmsg = (char_u *)_("E508: Can't read file for backup (add ! to override)"); 3356 #ifdef UNIX 3357 set_file_time(backup, st_old.st_atime, st_old.st_mtime); 3358 #endif 3359 #ifdef HAVE_ACL 3360 mch_set_acl(backup, acl); 3361 #endif 3362 break; 3363 } 3364 } 3365 } 3366 nobackup: 3367 close(fd); /* ignore errors for closing read file */ 3368 vim_free(copybuf); 3369 3370 if (backup == NULL && errmsg == NULL) 3371 errmsg = (char_u *)_("E509: Cannot create backup file (add ! to override)"); 3372 /* ignore errors when forceit is TRUE */ 3373 if ((some_error || errmsg != NULL) && !forceit) 3374 { 3375 retval = FAIL; 3376 goto fail; 3377 } 3378 errmsg = NULL; 3379 } 3380 else 3381 { 3382 char_u *dirp; 3383 char_u *p; 3384 char_u *rootname; 3385 3386 /* 3387 * Make a backup by renaming the original file. 3388 */ 3389 /* 3390 * If 'cpoptions' includes the "W" flag, we don't want to 3391 * overwrite a read-only file. But rename may be possible 3392 * anyway, thus we need an extra check here. 3393 */ 3394 if (file_readonly && vim_strchr(p_cpo, CPO_FWRITE) != NULL) 3395 { 3396 errnum = (char_u *)"E504: "; 3397 errmsg = (char_u *)_(err_readonly); 3398 goto fail; 3399 } 3400 3401 /* 3402 * 3403 * Form the backup file name - change path/fo.o.h to 3404 * path/fo.o.h.bak Try all directories in 'backupdir', first one 3405 * that works is used. 3406 */ 3407 dirp = p_bdir; 3408 while (*dirp) 3409 { 3410 /* 3411 * Isolate one directory name and make the backup file name. 3412 */ 3413 (void)copy_option_part(&dirp, IObuff, IOSIZE, ","); 3414 rootname = get_file_in_dir(fname, IObuff); 3415 if (rootname == NULL) 3416 backup = NULL; 3417 else 3418 { 3419 backup = buf_modname( 3420 #ifdef SHORT_FNAME 3421 TRUE, 3422 #else 3423 (buf->b_p_sn || buf->b_shortname), 3424 #endif 3425 rootname, backup_ext, FALSE); 3426 vim_free(rootname); 3427 } 3428 3429 if (backup != NULL) 3430 { 3431 /* 3432 * If we are not going to keep the backup file, don't 3433 * delete an existing one, try to use another name. 3434 * Change one character, just before the extension. 3435 */ 3436 if (!p_bk && mch_getperm(backup) >= 0) 3437 { 3438 p = backup + STRLEN(backup) - 1 - STRLEN(backup_ext); 3439 if (p < backup) /* empty file name ??? */ 3440 p = backup; 3441 *p = 'z'; 3442 while (*p > 'a' && mch_getperm(backup) >= 0) 3443 --*p; 3444 /* They all exist??? Must be something wrong! */ 3445 if (*p == 'a') 3446 { 3447 vim_free(backup); 3448 backup = NULL; 3449 } 3450 } 3451 } 3452 if (backup != NULL) 3453 { 3454 3455 /* 3456 * Delete any existing backup and move the current version to 3457 * the backup. For safety, we don't remove the backup until 3458 * the write has finished successfully. And if the 'backup' 3459 * option is set, leave it around. 3460 */ 3461 /* 3462 * If the renaming of the original file to the backup file 3463 * works, quit here. 3464 */ 3465 if (vim_rename(fname, backup) == 0) 3466 break; 3467 3468 vim_free(backup); /* don't do the rename below */ 3469 backup = NULL; 3470 } 3471 } 3472 if (backup == NULL && !forceit) 3473 { 3474 errmsg = (char_u *)_("E510: Can't make backup file (add ! to override)"); 3475 goto fail; 3476 } 3477 } 3478 } 3479 3480 #if defined(UNIX) && !defined(ARCHIE) 3481 /* When using ":w!" and the file was read-only: make it writable */ 3482 if (forceit && perm >= 0 && !(perm & 0200) && st_old.st_uid == getuid() 3483 && vim_strchr(p_cpo, CPO_FWRITE) == NULL) 3484 { 3485 perm |= 0200; 3486 (void)mch_setperm(fname, perm); 3487 made_writable = TRUE; 3488 } 3489 #endif 3490 3491 /* When using ":w!" and writing to the current file, readonly makes no 3492 * sense, reset it */ 3493 if (forceit && overwriting) 3494 { 3495 buf->b_p_ro = FALSE; 3496 #ifdef FEAT_TITLE 3497 need_maketitle = TRUE; /* set window title later */ 3498 #endif 3499 #ifdef FEAT_WINDOWS 3500 status_redraw_all(); /* redraw status lines later */ 3501 #endif 3502 } 3503 3504 if (end > buf->b_ml.ml_line_count) 3505 end = buf->b_ml.ml_line_count; 3506 if (buf->b_ml.ml_flags & ML_EMPTY) 3507 start = end + 1; 3508 3509 /* 3510 * If the original file is being overwritten, there is a small chance that 3511 * we crash in the middle of writing. Therefore the file is preserved now. 3512 * This makes all block numbers positive so that recovery does not need 3513 * the original file. 3514 * Don't do this if there is a backup file and we are exiting. 3515 */ 3516 if (reset_changed && !newfile && !otherfile(ffname) 3517 && !(exiting && backup != NULL)) 3518 { 3519 ml_preserve(buf, FALSE); 3520 if (got_int) 3521 { 3522 errmsg = (char_u *)_(e_interr); 3523 goto restore_backup; 3524 } 3525 } 3526 3527 #ifdef MACOS_CLASSIC /* TODO: Is it need for MACOS_X? (Dany) */ 3528 /* 3529 * Before risking to lose the original file verify if there's 3530 * a resource fork to preserve, and if cannot be done warn 3531 * the users. This happens when overwriting without backups. 3532 */ 3533 if (backup == NULL && overwriting && !append) 3534 if (mch_has_resource_fork(fname)) 3535 { 3536 errmsg = (char_u *)_("E460: The resource fork would be lost (add ! to override)"); 3537 goto restore_backup; 3538 } 3539 #endif 3540 3541 #ifdef VMS 3542 vms_remove_version(fname); /* remove version */ 3543 #endif 3544 /* Default: write the the file directly. May write to a temp file for 3545 * multi-byte conversion. */ 3546 wfname = fname; 3547 3548 #ifdef FEAT_MBYTE 3549 /* Check for forced 'fileencoding' from "++opt=val" argument. */ 3550 if (eap != NULL && eap->force_enc != 0) 3551 { 3552 fenc = eap->cmd + eap->force_enc; 3553 fenc = enc_canonize(fenc); 3554 fenc_tofree = fenc; 3555 } 3556 else 3557 fenc = buf->b_p_fenc; 3558 3559 /* 3560 * The file needs to be converted when 'fileencoding' is set and 3561 * 'fileencoding' differs from 'encoding'. 3562 */ 3563 converted = (*fenc != NUL && !same_encoding(p_enc, fenc)); 3564 3565 /* 3566 * Check if UTF-8 to UCS-2/4 or Latin1 conversion needs to be done. Or 3567 * Latin1 to Unicode conversion. This is handled in buf_write_bytes(). 3568 * Prepare the flags for it and allocate bw_conv_buf when needed. 3569 */ 3570 if (converted && (enc_utf8 || STRCMP(p_enc, "latin1") == 0)) 3571 { 3572 wb_flags = get_fio_flags(fenc); 3573 if (wb_flags & (FIO_UCS2 | FIO_UCS4 | FIO_UTF16 | FIO_UTF8)) 3574 { 3575 /* Need to allocate a buffer to translate into. */ 3576 if (wb_flags & (FIO_UCS2 | FIO_UTF16 | FIO_UTF8)) 3577 write_info.bw_conv_buflen = bufsize * 2; 3578 else /* FIO_UCS4 */ 3579 write_info.bw_conv_buflen = bufsize * 4; 3580 write_info.bw_conv_buf 3581 = lalloc((long_u)write_info.bw_conv_buflen, TRUE); 3582 if (write_info.bw_conv_buf == NULL) 3583 end = 0; 3584 } 3585 } 3586 3587 # ifdef WIN3264 3588 if (converted && wb_flags == 0 && (wb_flags = get_win_fio_flags(fenc)) != 0) 3589 { 3590 /* Convert UTF-8 -> UCS-2 and UCS-2 -> DBCS. Worst-case * 4: */ 3591 write_info.bw_conv_buflen = bufsize * 4; 3592 write_info.bw_conv_buf 3593 = lalloc((long_u)write_info.bw_conv_buflen, TRUE); 3594 if (write_info.bw_conv_buf == NULL) 3595 end = 0; 3596 } 3597 # endif 3598 3599 # ifdef MACOS_X 3600 if (converted && wb_flags == 0 && (wb_flags = get_mac_fio_flags(fenc)) != 0) 3601 { 3602 write_info.bw_conv_buflen = bufsize * 3; 3603 write_info.bw_conv_buf 3604 = lalloc((long_u)write_info.bw_conv_buflen, TRUE); 3605 if (write_info.bw_conv_buf == NULL) 3606 end = 0; 3607 } 3608 # endif 3609 3610 # if defined(FEAT_EVAL) || defined(USE_ICONV) 3611 if (converted && wb_flags == 0) 3612 { 3613 # ifdef USE_ICONV 3614 /* 3615 * Use iconv() conversion when conversion is needed and it's not done 3616 * internally. 3617 */ 3618 write_info.bw_iconv_fd = (iconv_t)my_iconv_open(fenc, 3619 enc_utf8 ? (char_u *)"utf-8" : p_enc); 3620 if (write_info.bw_iconv_fd != (iconv_t)-1) 3621 { 3622 /* We're going to use iconv(), allocate a buffer to convert in. */ 3623 write_info.bw_conv_buflen = bufsize * ICONV_MULT; 3624 write_info.bw_conv_buf 3625 = lalloc((long_u)write_info.bw_conv_buflen, TRUE); 3626 if (write_info.bw_conv_buf == NULL) 3627 end = 0; 3628 write_info.bw_first = TRUE; 3629 } 3630 # ifdef FEAT_EVAL 3631 else 3632 # endif 3633 # endif 3634 3635 # ifdef FEAT_EVAL 3636 /* 3637 * When the file needs to be converted with 'charconvert' after 3638 * writing, write to a temp file instead and let the conversion 3639 * overwrite the original file. 3640 */ 3641 if (*p_ccv != NUL) 3642 { 3643 wfname = vim_tempname('w'); 3644 if (wfname == NULL) /* Can't write without a tempfile! */ 3645 { 3646 errmsg = (char_u *)_("E214: Can't find temp file for writing"); 3647 goto restore_backup; 3648 } 3649 } 3650 # endif 3651 } 3652 # endif 3653 if (converted && wb_flags == 0 3654 # ifdef USE_ICONV 3655 && write_info.bw_iconv_fd == (iconv_t)-1 3656 # endif 3657 # ifdef FEAT_EVAL 3658 && wfname == fname 3659 # endif 3660 ) 3661 { 3662 if (!forceit) 3663 { 3664 errmsg = (char_u *)_("E213: Cannot convert (add ! to write without conversion)"); 3665 goto restore_backup; 3666 } 3667 notconverted = TRUE; 3668 } 3669 #endif 3670 3671 /* 3672 * Open the file "wfname" for writing. 3673 * We may try to open the file twice: If we can't write to the 3674 * file and forceit is TRUE we delete the existing file and try to create 3675 * a new one. If this still fails we may have lost the original file! 3676 * (this may happen when the user reached his quotum for number of files). 3677 * Appending will fail if the file does not exist and forceit is FALSE. 3678 */ 3679 while ((fd = mch_open((char *)wfname, O_WRONLY | O_EXTRA | (append 3680 ? (forceit ? (O_APPEND | O_CREAT) : O_APPEND) 3681 : (O_CREAT | O_TRUNC)) 3682 , 0666)) < 0) 3683 { 3684 /* 3685 * A forced write will try to create a new file if the old one is 3686 * still readonly. This may also happen when the directory is 3687 * read-only. In that case the mch_remove() will fail. 3688 */ 3689 if (errmsg == NULL) 3690 { 3691 #ifdef UNIX 3692 struct stat st; 3693 3694 /* Don't delete the file when it's a hard or symbolic link. */ 3695 if ((!newfile && st_old.st_nlink > 1) 3696 || (mch_lstat((char *)fname, &st) == 0 3697 && (st.st_dev != st_old.st_dev 3698 || st.st_ino != st_old.st_ino))) 3699 errmsg = (char_u *)_("E166: Can't open linked file for writing"); 3700 else 3701 #endif 3702 { 3703 errmsg = (char_u *)_("E212: Can't open file for writing"); 3704 if (forceit && vim_strchr(p_cpo, CPO_FWRITE) == NULL 3705 && perm >= 0) 3706 { 3707 #ifdef UNIX 3708 /* we write to the file, thus it should be marked 3709 writable after all */ 3710 if (!(perm & 0200)) 3711 made_writable = TRUE; 3712 perm |= 0200; 3713 if (st_old.st_uid != getuid() || st_old.st_gid != getgid()) 3714 perm &= 0777; 3715 #endif 3716 if (!append) /* don't remove when appending */ 3717 mch_remove(wfname); 3718 continue; 3719 } 3720 } 3721 } 3722 3723 restore_backup: 3724 { 3725 struct stat st; 3726 3727 /* 3728 * If we failed to open the file, we don't need a backup. Throw it 3729 * away. If we moved or removed the original file try to put the 3730 * backup in its place. 3731 */ 3732 if (backup != NULL && wfname == fname) 3733 { 3734 if (backup_copy) 3735 { 3736 /* 3737 * There is a small chance that we removed the original, 3738 * try to move the copy in its place. 3739 * This may not work if the vim_rename() fails. 3740 * In that case we leave the copy around. 3741 */ 3742 /* If file does not exist, put the copy in its place */ 3743 if (mch_stat((char *)fname, &st) < 0) 3744 vim_rename(backup, fname); 3745 /* if original file does exist throw away the copy */ 3746 if (mch_stat((char *)fname, &st) >= 0) 3747 mch_remove(backup); 3748 } 3749 else 3750 { 3751 /* try to put the original file back */ 3752 vim_rename(backup, fname); 3753 } 3754 } 3755 3756 /* if original file no longer exists give an extra warning */ 3757 if (!newfile && mch_stat((char *)fname, &st) < 0) 3758 end = 0; 3759 } 3760 3761 #ifdef FEAT_MBYTE 3762 if (wfname != fname) 3763 vim_free(wfname); 3764 #endif 3765 goto fail; 3766 } 3767 errmsg = NULL; 3768 3769 #if defined(MACOS_CLASSIC) || defined(WIN3264) 3770 /* TODO: Is it need for MACOS_X? (Dany) */ 3771 /* 3772 * On macintosh copy the original files attributes (i.e. the backup) 3773 * This is done in order to preserve the ressource fork and the 3774 * Finder attribute (label, comments, custom icons, file creatore) 3775 */ 3776 if (backup != NULL && overwriting && !append) 3777 { 3778 if (backup_copy) 3779 (void)mch_copy_file_attribute(wfname, backup); 3780 else 3781 (void)mch_copy_file_attribute(backup, wfname); 3782 } 3783 3784 if (!overwriting && !append) 3785 { 3786 if (buf->b_ffname != NULL) 3787 (void)mch_copy_file_attribute(buf->b_ffname, wfname); 3788 /* Should copy ressource fork */ 3789 } 3790 #endif 3791 3792 write_info.bw_fd = fd; 3793 3794 #ifdef FEAT_CRYPT 3795 if (*buf->b_p_key && !filtering) 3796 { 3797 crypt_init_keys(buf->b_p_key); 3798 /* Write magic number, so that Vim knows that this file is encrypted 3799 * when reading it again. This also undergoes utf-8 to ucs-2/4 3800 * conversion when needed. */ 3801 write_info.bw_buf = (char_u *)CRYPT_MAGIC; 3802 write_info.bw_len = CRYPT_MAGIC_LEN; 3803 write_info.bw_flags = FIO_NOCONVERT; 3804 if (buf_write_bytes(&write_info) == FAIL) 3805 end = 0; 3806 wb_flags |= FIO_ENCRYPTED; 3807 } 3808 #endif 3809 3810 write_info.bw_buf = buffer; 3811 nchars = 0; 3812 3813 /* use "++bin", "++nobin" or 'binary' */ 3814 if (eap != NULL && eap->force_bin != 0) 3815 write_bin = (eap->force_bin == FORCE_BIN); 3816 else 3817 write_bin = buf->b_p_bin; 3818 3819 #ifdef FEAT_MBYTE 3820 /* 3821 * The BOM is written just after the encryption magic number. 3822 */ 3823 if (buf->b_p_bomb && !write_bin) 3824 { 3825 write_info.bw_len = make_bom(buffer, fenc); 3826 if (write_info.bw_len > 0) 3827 { 3828 /* don't convert, do encryption */ 3829 write_info.bw_flags = FIO_NOCONVERT | wb_flags; 3830 if (buf_write_bytes(&write_info) == FAIL) 3831 end = 0; 3832 else 3833 nchars += write_info.bw_len; 3834 } 3835 } 3836 #endif 3837 3838 write_info.bw_len = bufsize; 3839 #ifdef HAS_BW_FLAGS 3840 write_info.bw_flags = wb_flags; 3841 #endif 3842 fileformat = get_fileformat_force(buf, eap); 3843 s = buffer; 3844 len = 0; 3845 for (lnum = start; lnum <= end; ++lnum) 3846 { 3847 /* 3848 * The next while loop is done once for each character written. 3849 * Keep it fast! 3850 */ 3851 ptr = ml_get_buf(buf, lnum, FALSE) - 1; 3852 while ((c = *++ptr) != NUL) 3853 { 3854 if (c == NL) 3855 *s = NUL; /* replace newlines with NULs */ 3856 else if (c == CAR && fileformat == EOL_MAC) 3857 *s = NL; /* Mac: replace CRs with NLs */ 3858 else 3859 *s = c; 3860 ++s; 3861 if (++len != bufsize) 3862 continue; 3863 if (buf_write_bytes(&write_info) == FAIL) 3864 { 3865 end = 0; /* write error: break loop */ 3866 break; 3867 } 3868 nchars += bufsize; 3869 s = buffer; 3870 len = 0; 3871 } 3872 /* write failed or last line has no EOL: stop here */ 3873 if (end == 0 3874 || (lnum == end 3875 && write_bin 3876 && (lnum == write_no_eol_lnum 3877 || (lnum == buf->b_ml.ml_line_count && !buf->b_p_eol)))) 3878 { 3879 ++lnum; /* written the line, count it */ 3880 no_eol = TRUE; 3881 break; 3882 } 3883 if (fileformat == EOL_UNIX) 3884 *s++ = NL; 3885 else 3886 { 3887 *s++ = CAR; /* EOL_MAC or EOL_DOS: write CR */ 3888 if (fileformat == EOL_DOS) /* write CR-NL */ 3889 { 3890 if (++len == bufsize) 3891 { 3892 if (buf_write_bytes(&write_info) == FAIL) 3893 { 3894 end = 0; /* write error: break loop */ 3895 break; 3896 } 3897 nchars += bufsize; 3898 s = buffer; 3899 len = 0; 3900 } 3901 *s++ = NL; 3902 } 3903 } 3904 if (++len == bufsize && end) 3905 { 3906 if (buf_write_bytes(&write_info) == FAIL) 3907 { 3908 end = 0; /* write error: break loop */ 3909 break; 3910 } 3911 nchars += bufsize; 3912 s = buffer; 3913 len = 0; 3914 3915 ui_breakcheck(); 3916 if (got_int) 3917 { 3918 end = 0; /* Interrupted, break loop */ 3919 break; 3920 } 3921 } 3922 #ifdef VMS 3923 /* 3924 * On VMS there is a problem: newlines get added when writing blocks 3925 * at a time. Fix it by writing a line at a time. 3926 * This is much slower! 3927 * Explanation: Vim can not handle, so far, variable record format. 3928 * With $analize/rms filename you can get the rms file structure, and 3929 * if the Record format filed is variable, CR will be added after 3930 * every written buffer. In other cases it works without this fix. 3931 * From other side read is about 5 times slower for "variable record 3932 * format" files. 3933 */ 3934 if (buf->b_fab_rfm == FAB$C_VAR) 3935 { 3936 write_info.bw_len = len; 3937 if (buf_write_bytes(&write_info) == FAIL) 3938 { 3939 end = 0; /* write error: break loop */ 3940 break; 3941 } 3942 write_info.bw_len = bufsize; 3943 nchars += len; 3944 s = buffer; 3945 len = 0; 3946 } 3947 #endif 3948 } 3949 if (len > 0 && end > 0) 3950 { 3951 write_info.bw_len = len; 3952 if (buf_write_bytes(&write_info) == FAIL) 3953 end = 0; /* write error */ 3954 nchars += len; 3955 } 3956 3957 #if defined(UNIX) && defined(HAVE_FSYNC) 3958 /* On many journalling file systems there is a bug that causes both the 3959 * original and the backup file to be lost when halting the system right 3960 * after writing the file. That's because only the meta-data is 3961 * journalled. Syncing the file slows down the system, but assures it has 3962 * been written to disk and we don't lose it. 3963 * For a device do try the fsync() but don't complain if it does not work 3964 * (could be a pipe). */ 3965 if (fsync(fd) != 0 && !device) 3966 { 3967 errmsg = (char_u *)_("E667: Fsync failed"); 3968 end = 0; 3969 } 3970 #endif 3971 3972 if (close(fd) != 0) 3973 { 3974 errmsg = (char_u *)_("E512: Close failed"); 3975 end = 0; 3976 } 3977 3978 #ifdef UNIX 3979 if (made_writable) 3980 perm &= ~0200; /* reset 'w' bit for security reasons */ 3981 #endif 3982 if (perm >= 0) /* set perm. of new file same as old file */ 3983 (void)mch_setperm(wfname, perm); 3984 #ifdef RISCOS 3985 if (!append && !filtering) 3986 /* Set the filetype after writing the file. */ 3987 mch_set_filetype(wfname, buf->b_p_oft); 3988 #endif 3989 #ifdef HAVE_ACL 3990 /* Probably need to set the ACL before changing the user (can't set the 3991 * ACL on a file the user doesn't own). */ 3992 if (!backup_copy) 3993 mch_set_acl(wfname, acl); 3994 #endif 3995 3996 #ifdef UNIX 3997 /* When creating a new file, set its owner/group to that of the original 3998 * file. Get the new device and inode number. */ 3999 if (backup != NULL && !backup_copy) 4000 { 4001 struct stat st; 4002 4003 /* don't change the owner when it's already OK, some systems remove 4004 * permission or ACL stuff */ 4005 if (mch_stat((char *)wfname, &st) < 0 4006 || st.st_uid != st_old.st_uid 4007 || st.st_gid != st_old.st_gid) 4008 { 4009 chown((char *)wfname, st_old.st_uid, st_old.st_gid); 4010 if (perm >= 0) /* set permission again, may have changed */ 4011 (void)mch_setperm(wfname, perm); 4012 } 4013 buf_setino(buf); 4014 } 4015 #endif 4016 4017 4018 #if defined(FEAT_MBYTE) && defined(FEAT_EVAL) 4019 if (wfname != fname) 4020 { 4021 /* 4022 * The file was written to a temp file, now it needs to be converted 4023 * with 'charconvert' to (overwrite) the output file. 4024 */ 4025 if (end != 0) 4026 { 4027 if (eval_charconvert(enc_utf8 ? (char_u *)"utf-8" : p_enc, fenc, 4028 wfname, fname) == FAIL) 4029 { 4030 write_info.bw_conv_error = TRUE; 4031 end = 0; 4032 } 4033 } 4034 mch_remove(wfname); 4035 vim_free(wfname); 4036 } 4037 #endif 4038 4039 if (end == 0) 4040 { 4041 if (errmsg == NULL) 4042 { 4043 #ifdef FEAT_MBYTE 4044 if (write_info.bw_conv_error) 4045 errmsg = (char_u *)_("E513: write error, conversion failed"); 4046 else 4047 #endif 4048 if (got_int) 4049 errmsg = (char_u *)_(e_interr); 4050 else 4051 errmsg = (char_u *)_("E514: write error (file system full?)"); 4052 } 4053 4054 /* 4055 * If we have a backup file, try to put it in place of the new file, 4056 * because the new file is probably corrupt. This avoids loosing the 4057 * original file when trying to make a backup when writing the file a 4058 * second time. 4059 * When "backup_copy" is set we need to copy the backup over the new 4060 * file. Otherwise rename the backup file. 4061 * If this is OK, don't give the extra warning message. 4062 */ 4063 if (backup != NULL) 4064 { 4065 if (backup_copy) 4066 { 4067 /* This may take a while, if we were interrupted let the user 4068 * know we got the message. */ 4069 if (got_int) 4070 { 4071 MSG(_(e_interr)); 4072 out_flush(); 4073 } 4074 if ((fd = mch_open((char *)backup, O_RDONLY | O_EXTRA, 0)) >= 0) 4075 { 4076 if ((write_info.bw_fd = mch_open((char *)fname, 4077 O_WRONLY | O_CREAT | O_TRUNC | O_EXTRA, 0666)) >= 0) 4078 { 4079 /* copy the file. */ 4080 write_info.bw_buf = smallbuf; 4081 #ifdef HAS_BW_FLAGS 4082 write_info.bw_flags = FIO_NOCONVERT; 4083 #endif 4084 while ((write_info.bw_len = vim_read(fd, smallbuf, 4085 SMBUFSIZE)) > 0) 4086 if (buf_write_bytes(&write_info) == FAIL) 4087 break; 4088 4089 if (close(write_info.bw_fd) >= 0 4090 && write_info.bw_len == 0) 4091 end = 1; /* success */ 4092 } 4093 close(fd); /* ignore errors for closing read file */ 4094 } 4095 } 4096 else 4097 { 4098 if (vim_rename(backup, fname) == 0) 4099 end = 1; 4100 } 4101 } 4102 goto fail; 4103 } 4104 4105 lnum -= start; /* compute number of written lines */ 4106 --no_wait_return; /* may wait for return now */ 4107 4108 #if !(defined(UNIX) || defined(VMS)) 4109 fname = sfname; /* use shortname now, for the messages */ 4110 #endif 4111 if (!filtering) 4112 { 4113 msg_add_fname(buf, fname); /* put fname in IObuff with quotes */ 4114 c = FALSE; 4115 #ifdef FEAT_MBYTE 4116 if (write_info.bw_conv_error) 4117 { 4118 STRCAT(IObuff, _(" CONVERSION ERROR")); 4119 c = TRUE; 4120 } 4121 else if (notconverted) 4122 { 4123 STRCAT(IObuff, _("[NOT converted]")); 4124 c = TRUE; 4125 } 4126 else if (converted) 4127 { 4128 STRCAT(IObuff, _("[converted]")); 4129 c = TRUE; 4130 } 4131 #endif 4132 if (device) 4133 { 4134 STRCAT(IObuff, _("[Device]")); 4135 c = TRUE; 4136 } 4137 else if (newfile) 4138 { 4139 STRCAT(IObuff, shortmess(SHM_NEW) ? _("[New]") : _("[New File]")); 4140 c = TRUE; 4141 } 4142 if (no_eol) 4143 { 4144 msg_add_eol(); 4145 c = TRUE; 4146 } 4147 /* may add [unix/dos/mac] */ 4148 if (msg_add_fileformat(fileformat)) 4149 c = TRUE; 4150 #ifdef FEAT_CRYPT 4151 if (wb_flags & FIO_ENCRYPTED) 4152 { 4153 STRCAT(IObuff, _("[crypted]")); 4154 c = TRUE; 4155 } 4156 #endif 4157 msg_add_lines(c, (long)lnum, nchars); /* add line/char count */ 4158 if (!shortmess(SHM_WRITE)) 4159 { 4160 if (append) 4161 STRCAT(IObuff, shortmess(SHM_WRI) ? _(" [a]") : _(" appended")); 4162 else 4163 STRCAT(IObuff, shortmess(SHM_WRI) ? _(" [w]") : _(" written")); 4164 } 4165 4166 set_keep_msg(msg_trunc_attr(IObuff, FALSE, 0)); 4167 keep_msg_attr = 0; 4168 } 4169 4170 if (reset_changed && whole 4171 #ifdef FEAT_MBYTE 4172 && !write_info.bw_conv_error 4173 #endif 4174 ) /* when written everything correctly */ 4175 { 4176 unchanged(buf, TRUE); 4177 u_unchanged(buf); 4178 } 4179 4180 /* 4181 * If written to the current file, update the timestamp of the swap file 4182 * and reset the BF_WRITE_MASK flags. Also sets buf->b_mtime. 4183 */ 4184 if (overwriting) 4185 { 4186 ml_timestamp(buf); 4187 buf->b_flags &= ~BF_WRITE_MASK; 4188 } 4189 4190 /* 4191 * If we kept a backup until now, and we are in patch mode, then we make 4192 * the backup file our 'original' file. 4193 */ 4194 if (*p_pm && dobackup) 4195 { 4196 char *org = (char *)buf_modname( 4197 #ifdef SHORT_FNAME 4198 TRUE, 4199 #else 4200 (buf->b_p_sn || buf->b_shortname), 4201 #endif 4202 fname, p_pm, FALSE); 4203 4204 if (backup != NULL) 4205 { 4206 struct stat st; 4207 4208 /* 4209 * If the original file does not exist yet 4210 * the current backup file becomes the original file 4211 */ 4212 if (org == NULL) 4213 EMSG(_("E205: Patchmode: can't save original file")); 4214 else if (mch_stat(org, &st) < 0) 4215 { 4216 vim_rename(backup, (char_u *)org); 4217 vim_free(backup); /* don't delete the file */ 4218 backup = NULL; 4219 #ifdef UNIX 4220 set_file_time((char_u *)org, st_old.st_atime, st_old.st_mtime); 4221 #endif 4222 } 4223 } 4224 /* 4225 * If there is no backup file, remember that a (new) file was 4226 * created. 4227 */ 4228 else 4229 { 4230 int empty_fd; 4231 4232 if (org == NULL 4233 || (empty_fd = mch_open(org, O_CREAT | O_EXTRA | O_EXCL, 4234 0666)) < 0) 4235 EMSG(_("E206: patchmode: can't touch empty original file")); 4236 else 4237 close(empty_fd); 4238 } 4239 if (org != NULL) 4240 { 4241 mch_setperm((char_u *)org, mch_getperm(fname) & 0777); 4242 vim_free(org); 4243 } 4244 } 4245 4246 /* 4247 * Remove the backup unless 'backup' option is set 4248 */ 4249 if (!p_bk && backup != NULL && mch_remove(backup) != 0) 4250 EMSG(_("E207: Can't delete backup file")); 4251 4252 #ifdef FEAT_SUN_WORKSHOP 4253 if (usingSunWorkShop) 4254 workshop_file_saved((char *) ffname); 4255 #endif 4256 4257 goto nofail; 4258 4259 /* 4260 * Finish up. We get here either after failure or success. 4261 */ 4262 fail: 4263 --no_wait_return; /* may wait for return now */ 4264 nofail: 4265 4266 /* Done saving, we accept changed buffer warnings again */ 4267 buf->b_saving = FALSE; 4268 4269 vim_free(backup); 4270 if (buffer != smallbuf) 4271 vim_free(buffer); 4272 #ifdef FEAT_MBYTE 4273 vim_free(fenc_tofree); 4274 vim_free(write_info.bw_conv_buf); 4275 # ifdef USE_ICONV 4276 if (write_info.bw_iconv_fd != (iconv_t)-1) 4277 { 4278 iconv_close(write_info.bw_iconv_fd); 4279 write_info.bw_iconv_fd = (iconv_t)-1; 4280 } 4281 # endif 4282 #endif 4283 #ifdef HAVE_ACL 4284 mch_free_acl(acl); 4285 #endif 4286 4287 if (errmsg != NULL) 4288 { 4289 int numlen = errnum != NULL ? STRLEN(errnum) : 0; 4290 4291 attr = hl_attr(HLF_E); /* set highlight for error messages */ 4292 msg_add_fname(buf, 4293 #ifndef UNIX 4294 sfname 4295 #else 4296 fname 4297 #endif 4298 ); /* put file name in IObuff with quotes */ 4299 if (STRLEN(IObuff) + STRLEN(errmsg) + numlen >= IOSIZE) 4300 IObuff[IOSIZE - STRLEN(errmsg) - numlen - 1] = NUL; 4301 /* If the error message has the form "is ...", put the error number in 4302 * front of the file name. */ 4303 if (errnum != NULL) 4304 { 4305 mch_memmove(IObuff + numlen, IObuff, STRLEN(IObuff) + 1); 4306 mch_memmove(IObuff, errnum, (size_t)numlen); 4307 } 4308 STRCAT(IObuff, errmsg); 4309 emsg(IObuff); 4310 4311 retval = FAIL; 4312 if (end == 0) 4313 { 4314 MSG_PUTS_ATTR(_("\nWARNING: Original file may be lost or damaged\n"), 4315 attr | MSG_HIST); 4316 MSG_PUTS_ATTR(_("don't quit the editor until the file is successfully written!"), 4317 attr | MSG_HIST); 4318 4319 /* Update the timestamp to avoid an "overwrite changed file" 4320 * prompt when writing again. */ 4321 if (mch_stat((char *)fname, &st_old) >= 0) 4322 { 4323 buf_store_time(buf, &st_old, fname); 4324 buf->b_mtime_read = buf->b_mtime; 4325 } 4326 } 4327 } 4328 msg_scroll = msg_save; 4329 4330 #ifdef FEAT_AUTOCMD 4331 #ifdef FEAT_EVAL 4332 if (!should_abort(retval)) 4333 #else 4334 if (!got_int) 4335 #endif 4336 { 4337 aco_save_T aco; 4338 4339 write_no_eol_lnum = 0; /* in case it was set by the previous read */ 4340 4341 /* 4342 * Apply POST autocommands. 4343 * Careful: The autocommands may call buf_write() recursively! 4344 */ 4345 aucmd_prepbuf(&aco, buf); 4346 4347 if (append) 4348 apply_autocmds_exarg(EVENT_FILEAPPENDPOST, fname, fname, 4349 FALSE, curbuf, eap); 4350 else if (filtering) 4351 apply_autocmds_exarg(EVENT_FILTERWRITEPOST, NULL, fname, 4352 FALSE, curbuf, eap); 4353 else if (reset_changed && whole) 4354 apply_autocmds_exarg(EVENT_BUFWRITEPOST, fname, fname, 4355 FALSE, curbuf, eap); 4356 else 4357 apply_autocmds_exarg(EVENT_FILEWRITEPOST, fname, fname, 4358 FALSE, curbuf, eap); 4359 4360 /* restore curwin/curbuf and a few other things */ 4361 aucmd_restbuf(&aco); 4362 4363 #ifdef FEAT_EVAL 4364 if (aborting()) /* autocmds may abort script processing */ 4365 retval = FALSE; 4366 #endif 4367 } 4368 #endif 4369 4370 got_int |= prev_got_int; 4371 4372 #ifdef MACOS_CLASSIC /* TODO: Is it need for MACOS_X? (Dany) */ 4373 /* Update machine specific information. */ 4374 mch_post_buffer_write(buf); 4375 #endif 4376 return retval; 4377 } 4378 4379 /* 4380 * Put file name into IObuff with quotes. 4381 */ 4382 static void 4383 msg_add_fname(buf, fname) 4384 buf_T *buf; 4385 char_u *fname; 4386 { 4387 if (fname == NULL) 4388 fname = (char_u *)"-stdin-"; 4389 home_replace(buf, fname, IObuff + 1, IOSIZE - 4, TRUE); 4390 IObuff[0] = '"'; 4391 STRCAT(IObuff, "\" "); 4392 } 4393 4394 /* 4395 * Append message for text mode to IObuff. 4396 * Return TRUE if something appended. 4397 */ 4398 static int 4399 msg_add_fileformat(eol_type) 4400 int eol_type; 4401 { 4402 #ifndef USE_CRNL 4403 if (eol_type == EOL_DOS) 4404 { 4405 STRCAT(IObuff, shortmess(SHM_TEXT) ? _("[dos]") : _("[dos format]")); 4406 return TRUE; 4407 } 4408 #endif 4409 #ifndef USE_CR 4410 if (eol_type == EOL_MAC) 4411 { 4412 STRCAT(IObuff, shortmess(SHM_TEXT) ? _("[mac]") : _("[mac format]")); 4413 return TRUE; 4414 } 4415 #endif 4416 #if defined(USE_CRNL) || defined(USE_CR) 4417 if (eol_type == EOL_UNIX) 4418 { 4419 STRCAT(IObuff, shortmess(SHM_TEXT) ? _("[unix]") : _("[unix format]")); 4420 return TRUE; 4421 } 4422 #endif 4423 return FALSE; 4424 } 4425 4426 /* 4427 * Append line and character count to IObuff. 4428 */ 4429 static void 4430 msg_add_lines(insert_space, lnum, nchars) 4431 int insert_space; 4432 long lnum; 4433 long nchars; 4434 { 4435 char_u *p; 4436 4437 p = IObuff + STRLEN(IObuff); 4438 4439 if (insert_space) 4440 *p++ = ' '; 4441 if (shortmess(SHM_LINES)) 4442 sprintf((char *)p, "%ldL, %ldC", lnum, nchars); 4443 else 4444 { 4445 if (lnum == 1) 4446 STRCPY(p, _("1 line, ")); 4447 else 4448 sprintf((char *)p, _("%ld lines, "), lnum); 4449 p += STRLEN(p); 4450 if (nchars == 1) 4451 STRCPY(p, _("1 character")); 4452 else 4453 sprintf((char *)p, _("%ld characters"), nchars); 4454 } 4455 } 4456 4457 /* 4458 * Append message for missing line separator to IObuff. 4459 */ 4460 static void 4461 msg_add_eol() 4462 { 4463 STRCAT(IObuff, shortmess(SHM_LAST) ? _("[noeol]") : _("[Incomplete last line]")); 4464 } 4465 4466 /* 4467 * Check modification time of file, before writing to it. 4468 * The size isn't checked, because using a tool like "gzip" takes care of 4469 * using the same timestamp but can't set the size. 4470 */ 4471 static int 4472 check_mtime(buf, st) 4473 buf_T *buf; 4474 struct stat *st; 4475 { 4476 if (buf->b_mtime_read != 0 4477 && time_differs((long)st->st_mtime, buf->b_mtime_read)) 4478 { 4479 msg_scroll = TRUE; /* don't overwrite messages here */ 4480 msg_silent = 0; /* must give this prompt */ 4481 /* don't use emsg() here, don't want to flush the buffers */ 4482 MSG_ATTR(_("WARNING: The file has been changed since reading it!!!"), 4483 hl_attr(HLF_E)); 4484 if (ask_yesno((char_u *)_("Do you really want to write to it"), 4485 TRUE) == 'n') 4486 return FAIL; 4487 msg_scroll = FALSE; /* always overwrite the file message now */ 4488 } 4489 return OK; 4490 } 4491 4492 static int 4493 time_differs(t1, t2) 4494 long t1, t2; 4495 { 4496 #if defined(__linux__) || defined(MSDOS) || defined(MSWIN) 4497 /* On a FAT filesystem, esp. under Linux, there are only 5 bits to store 4498 * the seconds. Since the roundoff is done when flushing the inode, the 4499 * time may change unexpectedly by one second!!! */ 4500 return (t1 - t2 > 1 || t2 - t1 > 1); 4501 #else 4502 return (t1 != t2); 4503 #endif 4504 } 4505 4506 /* 4507 * Call write() to write a number of bytes to the file. 4508 * Also handles encryption and 'encoding' conversion. 4509 * 4510 * Return FAIL for failure, OK otherwise. 4511 */ 4512 static int 4513 buf_write_bytes(ip) 4514 struct bw_info *ip; 4515 { 4516 int wlen; 4517 char_u *buf = ip->bw_buf; /* data to write */ 4518 int len = ip->bw_len; /* length of data */ 4519 #ifdef HAS_BW_FLAGS 4520 int flags = ip->bw_flags; /* extra flags */ 4521 #endif 4522 4523 #ifdef FEAT_MBYTE 4524 /* 4525 * Skip conversion when writing the crypt magic number or the BOM. 4526 */ 4527 if (!(flags & FIO_NOCONVERT)) 4528 { 4529 char_u *p; 4530 unsigned c; 4531 int n; 4532 4533 if (flags & FIO_UTF8) 4534 { 4535 /* 4536 * Convert latin1 in the buffer to UTF-8 in the file. 4537 */ 4538 p = ip->bw_conv_buf; /* translate to buffer */ 4539 for (wlen = 0; wlen < len; ++wlen) 4540 p += utf_char2bytes(buf[wlen], p); 4541 buf = ip->bw_conv_buf; 4542 len = (int)(p - ip->bw_conv_buf); 4543 } 4544 else if (flags & (FIO_UCS4 | FIO_UTF16 | FIO_UCS2 | FIO_LATIN1)) 4545 { 4546 /* 4547 * Convert UTF-8 bytes in the buffer to UCS-2, UCS-4, UTF-16 or 4548 * Latin1 chars in the file. 4549 */ 4550 if (flags & FIO_LATIN1) 4551 p = buf; /* translate in-place (can only get shorter) */ 4552 else 4553 p = ip->bw_conv_buf; /* translate to buffer */ 4554 for (wlen = 0; wlen < len; wlen += n) 4555 { 4556 if (wlen == 0 && ip->bw_restlen != 0) 4557 { 4558 int l; 4559 4560 /* Use remainder of previous call. Append the start of 4561 * buf[] to get a full sequence. Might still be too 4562 * short! */ 4563 l = CONV_RESTLEN - ip->bw_restlen; 4564 if (l > len) 4565 l = len; 4566 mch_memmove(ip->bw_rest + ip->bw_restlen, buf, (size_t)l); 4567 n = utf_ptr2len_check_len(ip->bw_rest, ip->bw_restlen + l); 4568 if (n > ip->bw_restlen + len) 4569 { 4570 /* We have an incomplete byte sequence at the end to 4571 * be written. We can't convert it without the 4572 * remaining bytes. Keep them for the next call. */ 4573 if (ip->bw_restlen + len > CONV_RESTLEN) 4574 return FAIL; 4575 ip->bw_restlen += len; 4576 break; 4577 } 4578 if (n > 1) 4579 c = utf_ptr2char(ip->bw_rest); 4580 else 4581 c = ip->bw_rest[0]; 4582 if (n >= ip->bw_restlen) 4583 { 4584 n -= ip->bw_restlen; 4585 ip->bw_restlen = 0; 4586 } 4587 else 4588 { 4589 ip->bw_restlen -= n; 4590 mch_memmove(ip->bw_rest, ip->bw_rest + n, 4591 (size_t)ip->bw_restlen); 4592 n = 0; 4593 } 4594 } 4595 else 4596 { 4597 n = utf_ptr2len_check_len(buf + wlen, len - wlen); 4598 if (n > len - wlen) 4599 { 4600 /* We have an incomplete byte sequence at the end to 4601 * be written. We can't convert it without the 4602 * remaining bytes. Keep them for the next call. */ 4603 if (len - wlen > CONV_RESTLEN) 4604 return FAIL; 4605 ip->bw_restlen = len - wlen; 4606 mch_memmove(ip->bw_rest, buf + wlen, 4607 (size_t)ip->bw_restlen); 4608 break; 4609 } 4610 if (n > 1) 4611 c = utf_ptr2char(buf + wlen); 4612 else 4613 c = buf[wlen]; 4614 } 4615 4616 ip->bw_conv_error |= ucs2bytes(c, &p, flags); 4617 } 4618 if (flags & FIO_LATIN1) 4619 len = (int)(p - buf); 4620 else 4621 { 4622 buf = ip->bw_conv_buf; 4623 len = (int)(p - ip->bw_conv_buf); 4624 } 4625 } 4626 4627 # ifdef WIN3264 4628 else if (flags & FIO_CODEPAGE) 4629 { 4630 /* 4631 * Convert UTF-8 or codepage to UCS-2 and then to MS-Windows 4632 * codepage. 4633 */ 4634 char_u *from; 4635 size_t fromlen; 4636 char_u *to; 4637 int u8c; 4638 BOOL bad = FALSE; 4639 int needed; 4640 4641 if (ip->bw_restlen > 0) 4642 { 4643 /* Need to concatenate the remainder of the previous call and 4644 * the bytes of the current call. Use the end of the 4645 * conversion buffer for this. */ 4646 fromlen = len + ip->bw_restlen; 4647 from = ip->bw_conv_buf + ip->bw_conv_buflen - fromlen; 4648 mch_memmove(from, ip->bw_rest, (size_t)ip->bw_restlen); 4649 mch_memmove(from + ip->bw_restlen, buf, (size_t)len); 4650 } 4651 else 4652 { 4653 from = buf; 4654 fromlen = len; 4655 } 4656 4657 to = ip->bw_conv_buf; 4658 if (enc_utf8) 4659 { 4660 /* Convert from UTF-8 to UCS-2, to the start of the buffer. 4661 * The buffer has been allocated to be big enough. */ 4662 while (fromlen > 0) 4663 { 4664 n = utf_ptr2len_check_len(from, fromlen); 4665 if (n > (int)fromlen) /* incomplete byte sequence */ 4666 break; 4667 u8c = utf_ptr2char(from); 4668 *to++ = (u8c & 0xff); 4669 *to++ = (u8c >> 8); 4670 fromlen -= n; 4671 from += n; 4672 } 4673 4674 /* Copy remainder to ip->bw_rest[] to be used for the next 4675 * call. */ 4676 if (fromlen > CONV_RESTLEN) 4677 { 4678 /* weird overlong sequence */ 4679 ip->bw_conv_error = TRUE; 4680 return FAIL; 4681 } 4682 mch_memmove(ip->bw_rest, from, fromlen); 4683 ip->bw_restlen = fromlen; 4684 } 4685 else 4686 { 4687 /* Convert from enc_codepage to UCS-2, to the start of the 4688 * buffer. The buffer has been allocated to be big enough. */ 4689 ip->bw_restlen = 0; 4690 needed = MultiByteToWideChar(enc_codepage, 4691 MB_ERR_INVALID_CHARS, (LPCSTR)from, fromlen, 4692 NULL, 0); 4693 if (needed == 0) 4694 { 4695 /* When conversion fails there may be a trailing byte. */ 4696 needed = MultiByteToWideChar(enc_codepage, 4697 MB_ERR_INVALID_CHARS, (LPCSTR)from, fromlen - 1, 4698 NULL, 0); 4699 if (needed == 0) 4700 { 4701 /* Conversion doesn't work. */ 4702 ip->bw_conv_error = TRUE; 4703 return FAIL; 4704 } 4705 /* Save the trailing byte for the next call. */ 4706 ip->bw_rest[0] = from[fromlen - 1]; 4707 ip->bw_restlen = 1; 4708 } 4709 needed = MultiByteToWideChar(enc_codepage, MB_ERR_INVALID_CHARS, 4710 (LPCSTR)from, fromlen - ip->bw_restlen, 4711 (LPWSTR)to, needed); 4712 if (needed == 0) 4713 { 4714 /* Safety check: Conversion doesn't work. */ 4715 ip->bw_conv_error = TRUE; 4716 return FAIL; 4717 } 4718 to += needed * 2; 4719 } 4720 4721 fromlen = to - ip->bw_conv_buf; 4722 buf = to; 4723 # ifdef CP_UTF8 /* VC 4.1 doesn't define CP_UTF8 */ 4724 if (FIO_GET_CP(flags) == CP_UTF8) 4725 { 4726 /* Convert from UCS-2 to UTF-8, using the remainder of the 4727 * conversion buffer. Fails when out of space. */ 4728 for (from = ip->bw_conv_buf; fromlen > 1; fromlen -= 2) 4729 { 4730 u8c = *from++; 4731 u8c += (*from++ << 8); 4732 to += utf_char2bytes(u8c, to); 4733 if (to + 6 >= ip->bw_conv_buf + ip->bw_conv_buflen) 4734 { 4735 ip->bw_conv_error = TRUE; 4736 return FAIL; 4737 } 4738 } 4739 len = to - buf; 4740 } 4741 else 4742 #endif 4743 { 4744 /* Convert from UCS-2 to the codepage, using the remainder of 4745 * the conversion buffer. If the conversion uses the default 4746 * character "0", the data doesn't fit in this encoding, so 4747 * fail. */ 4748 len = WideCharToMultiByte(FIO_GET_CP(flags), 0, 4749 (LPCWSTR)ip->bw_conv_buf, (int)fromlen / sizeof(WCHAR), 4750 (LPSTR)to, ip->bw_conv_buflen - fromlen, 0, &bad); 4751 if (bad) 4752 { 4753 ip->bw_conv_error = TRUE; 4754 return FAIL; 4755 } 4756 } 4757 } 4758 # endif 4759 4760 # ifdef MACOS_X 4761 else if (flags & FIO_MACROMAN) 4762 { 4763 /* 4764 * Convert UTF-8 or latin1 to Apple MacRoman. 4765 */ 4766 char_u *from; 4767 size_t fromlen; 4768 extern int enc2macroman __ARGS((char_u *from, size_t fromlen, 4769 char_u *to, int *tolenp, int maxtolen, char_u *rest, 4770 int *restlenp)); 4771 4772 if (ip->bw_restlen > 0) 4773 { 4774 /* Need to concatenate the remainder of the previous call and 4775 * the bytes of the current call. Use the end of the 4776 * conversion buffer for this. */ 4777 fromlen = len + ip->bw_restlen; 4778 from = ip->bw_conv_buf + ip->bw_conv_buflen - fromlen; 4779 mch_memmove(from, ip->bw_rest, (size_t)ip->bw_restlen); 4780 mch_memmove(from + ip->bw_restlen, buf, (size_t)len); 4781 } 4782 else 4783 { 4784 from = buf; 4785 fromlen = len; 4786 } 4787 4788 if (enc2macroman(from, fromlen, 4789 ip->bw_conv_buf, &len, ip->bw_conv_buflen, 4790 ip->bw_rest, &ip->bw_restlen) == FAIL) 4791 { 4792 ip->bw_conv_error = TRUE; 4793 return FAIL; 4794 } 4795 buf = ip->bw_conv_buf; 4796 } 4797 # endif 4798 4799 # ifdef USE_ICONV 4800 if (ip->bw_iconv_fd != (iconv_t)-1) 4801 { 4802 const char *from; 4803 size_t fromlen; 4804 char *to; 4805 size_t tolen; 4806 4807 /* Convert with iconv(). */ 4808 if (ip->bw_restlen > 0) 4809 { 4810 /* Need to concatenate the remainder of the previous call and 4811 * the bytes of the current call. Use the end of the 4812 * conversion buffer for this. */ 4813 fromlen = len + ip->bw_restlen; 4814 from = (char *)ip->bw_conv_buf + ip->bw_conv_buflen - fromlen; 4815 mch_memmove((void *)from, ip->bw_rest, (size_t)ip->bw_restlen); 4816 mch_memmove((void *)(from + ip->bw_restlen), buf, (size_t)len); 4817 tolen = ip->bw_conv_buflen - fromlen; 4818 } 4819 else 4820 { 4821 from = (const char *)buf; 4822 fromlen = len; 4823 tolen = ip->bw_conv_buflen; 4824 } 4825 to = (char *)ip->bw_conv_buf; 4826 4827 if (ip->bw_first) 4828 { 4829 size_t save_len = tolen; 4830 4831 /* output the initial shift state sequence */ 4832 (void)iconv(ip->bw_iconv_fd, NULL, NULL, &to, &tolen); 4833 4834 /* There is a bug in iconv() on Linux (which appears to be 4835 * wide-spread) which sets "to" to NULL and messes up "tolen". 4836 */ 4837 if (to == NULL) 4838 { 4839 to = (char *)ip->bw_conv_buf; 4840 tolen = save_len; 4841 } 4842 ip->bw_first = FALSE; 4843 } 4844 4845 /* 4846 * If iconv() has an error or there is not enough room, fail. 4847 */ 4848 if ((iconv(ip->bw_iconv_fd, (void *)&from, &fromlen, &to, &tolen) 4849 == (size_t)-1 && ICONV_ERRNO != ICONV_EINVAL) 4850 || fromlen > CONV_RESTLEN) 4851 { 4852 ip->bw_conv_error = TRUE; 4853 return FAIL; 4854 } 4855 4856 /* copy remainder to ip->bw_rest[] to be used for the next call. */ 4857 if (fromlen > 0) 4858 mch_memmove(ip->bw_rest, (void *)from, fromlen); 4859 ip->bw_restlen = (int)fromlen; 4860 4861 buf = ip->bw_conv_buf; 4862 len = (int)((char_u *)to - ip->bw_conv_buf); 4863 } 4864 # endif 4865 } 4866 #endif /* FEAT_MBYTE */ 4867 4868 #ifdef FEAT_CRYPT 4869 if (flags & FIO_ENCRYPTED) /* encrypt the data */ 4870 { 4871 int ztemp, t, i; 4872 4873 for (i = 0; i < len; i++) 4874 { 4875 ztemp = buf[i]; 4876 buf[i] = ZENCODE(ztemp, t); 4877 } 4878 } 4879 #endif 4880 4881 /* Repeat the write(), it may be interrupted by a signal. */ 4882 while (len) 4883 { 4884 wlen = vim_write(ip->bw_fd, buf, len); 4885 if (wlen <= 0) /* error! */ 4886 return FAIL; 4887 len -= wlen; 4888 buf += wlen; 4889 } 4890 return OK; 4891 } 4892 4893 #ifdef FEAT_MBYTE 4894 /* 4895 * Convert a Unicode character to bytes. 4896 */ 4897 static int 4898 ucs2bytes(c, pp, flags) 4899 unsigned c; /* in: character */ 4900 char_u **pp; /* in/out: pointer to result */ 4901 int flags; /* FIO_ flags */ 4902 { 4903 char_u *p = *pp; 4904 int error = FALSE; 4905 int cc; 4906 4907 4908 if (flags & FIO_UCS4) 4909 { 4910 if (flags & FIO_ENDIAN_L) 4911 { 4912 *p++ = c; 4913 *p++ = (c >> 8); 4914 *p++ = (c >> 16); 4915 *p++ = (c >> 24); 4916 } 4917 else 4918 { 4919 *p++ = (c >> 24); 4920 *p++ = (c >> 16); 4921 *p++ = (c >> 8); 4922 *p++ = c; 4923 } 4924 } 4925 else if (flags & (FIO_UCS2 | FIO_UTF16)) 4926 { 4927 if (c >= 0x10000) 4928 { 4929 if (flags & FIO_UTF16) 4930 { 4931 /* Make two words, ten bits of the character in each. First 4932 * word is 0xd800 - 0xdbff, second one 0xdc00 - 0xdfff */ 4933 c -= 0x10000; 4934 if (c >= 0x100000) 4935 error = TRUE; 4936 cc = ((c >> 10) & 0x3ff) + 0xd800; 4937 if (flags & FIO_ENDIAN_L) 4938 { 4939 *p++ = cc; 4940 *p++ = ((unsigned)cc >> 8); 4941 } 4942 else 4943 { 4944 *p++ = ((unsigned)cc >> 8); 4945 *p++ = cc; 4946 } 4947 c = (c & 0x3ff) + 0xdc00; 4948 } 4949 else 4950 error = TRUE; 4951 } 4952 if (flags & FIO_ENDIAN_L) 4953 { 4954 *p++ = c; 4955 *p++ = (c >> 8); 4956 } 4957 else 4958 { 4959 *p++ = (c >> 8); 4960 *p++ = c; 4961 } 4962 } 4963 else /* Latin1 */ 4964 { 4965 if (c >= 0x100) 4966 { 4967 error = TRUE; 4968 *p++ = 0xBF; 4969 } 4970 else 4971 *p++ = c; 4972 } 4973 4974 *pp = p; 4975 return error; 4976 } 4977 4978 /* 4979 * Return TRUE if "a" and "b" are the same 'encoding'. 4980 * Ignores difference between "ansi" and "latin1", "ucs-4" and "ucs-4be", etc. 4981 */ 4982 static int 4983 same_encoding(a, b) 4984 char_u *a; 4985 char_u *b; 4986 { 4987 int f; 4988 4989 if (STRCMP(a, b) == 0) 4990 return TRUE; 4991 f = get_fio_flags(a); 4992 return (f != 0 && get_fio_flags(b) == f); 4993 } 4994 4995 /* 4996 * Check "ptr" for a unicode encoding and return the FIO_ flags needed for the 4997 * internal conversion. 4998 * if "ptr" is an empty string, use 'encoding'. 4999 */ 5000 static int 5001 get_fio_flags(ptr) 5002 char_u *ptr; 5003 { 5004 int prop; 5005 5006 if (*ptr == NUL) 5007 ptr = p_enc; 5008 5009 prop = enc_canon_props(ptr); 5010 if (prop & ENC_UNICODE) 5011 { 5012 if (prop & ENC_2BYTE) 5013 { 5014 if (prop & ENC_ENDIAN_L) 5015 return FIO_UCS2 | FIO_ENDIAN_L; 5016 return FIO_UCS2; 5017 } 5018 if (prop & ENC_4BYTE) 5019 { 5020 if (prop & ENC_ENDIAN_L) 5021 return FIO_UCS4 | FIO_ENDIAN_L; 5022 return FIO_UCS4; 5023 } 5024 if (prop & ENC_2WORD) 5025 { 5026 if (prop & ENC_ENDIAN_L) 5027 return FIO_UTF16 | FIO_ENDIAN_L; 5028 return FIO_UTF16; 5029 } 5030 return FIO_UTF8; 5031 } 5032 if (prop & ENC_LATIN1) 5033 return FIO_LATIN1; 5034 /* must be ENC_DBCS, requires iconv() */ 5035 return 0; 5036 } 5037 5038 #ifdef WIN3264 5039 /* 5040 * Check "ptr" for a MS-Windows codepage name and return the FIO_ flags needed 5041 * for the conversion MS-Windows can do for us. Also accept "utf-8". 5042 * Used for conversion between 'encoding' and 'fileencoding'. 5043 */ 5044 static int 5045 get_win_fio_flags(ptr) 5046 char_u *ptr; 5047 { 5048 int cp; 5049 5050 /* Cannot do this when 'encoding' is not utf-8 and not a codepage. */ 5051 if (!enc_utf8 && enc_codepage <= 0) 5052 return 0; 5053 5054 cp = encname2codepage(ptr); 5055 if (cp == 0) 5056 { 5057 # ifdef CP_UTF8 /* VC 4.1 doesn't define CP_UTF8 */ 5058 if (STRCMP(ptr, "utf-8") == 0) 5059 cp = CP_UTF8; 5060 else 5061 # endif 5062 return 0; 5063 } 5064 return FIO_PUT_CP(cp) | FIO_CODEPAGE; 5065 } 5066 #endif 5067 5068 #ifdef MACOS_X 5069 /* 5070 * Check "ptr" for a Carbon supported encoding and return the FIO_ flags 5071 * needed for the internal conversion to/from utf-8 or latin1. 5072 */ 5073 static int 5074 get_mac_fio_flags(ptr) 5075 char_u *ptr; 5076 { 5077 if ((enc_utf8 || STRCMP(p_enc, "latin1") == 0) 5078 && (enc_canon_props(ptr) & ENC_MACROMAN)) 5079 return FIO_MACROMAN; 5080 return 0; 5081 } 5082 #endif 5083 5084 /* 5085 * Check for a Unicode BOM (Byte Order Mark) at the start of p[size]. 5086 * "size" must be at least 2. 5087 * Return the name of the encoding and set "*lenp" to the length. 5088 * Returns NULL when no BOM found. 5089 */ 5090 static char_u * 5091 check_for_bom(p, size, lenp, flags) 5092 char_u *p; 5093 long size; 5094 int *lenp; 5095 int flags; 5096 { 5097 char *name = NULL; 5098 int len = 2; 5099 5100 if (p[0] == 0xef && p[1] == 0xbb && size >= 3 && p[2] == 0xbf 5101 && (flags == FIO_ALL || flags == 0)) 5102 { 5103 name = "utf-8"; /* EF BB BF */ 5104 len = 3; 5105 } 5106 else if (p[0] == 0xff && p[1] == 0xfe) 5107 { 5108 if (size >= 4 && p[2] == 0 && p[3] == 0 5109 && (flags == FIO_ALL || flags == (FIO_UCS4 | FIO_ENDIAN_L))) 5110 { 5111 name = "ucs-4le"; /* FF FE 00 00 */ 5112 len = 4; 5113 } 5114 else if (flags == FIO_ALL || flags == (FIO_UCS2 | FIO_ENDIAN_L)) 5115 name = "ucs-2le"; /* FF FE */ 5116 else if (flags == (FIO_UTF16 | FIO_ENDIAN_L)) 5117 name = "utf-16le"; /* FF FE */ 5118 } 5119 else if (p[0] == 0xfe && p[1] == 0xff 5120 && (flags == FIO_ALL || flags == FIO_UCS2 || flags == FIO_UTF16)) 5121 { 5122 if (flags == FIO_UTF16) 5123 name = "utf-16"; /* FE FF */ 5124 else 5125 name = "ucs-2"; /* FE FF */ 5126 } 5127 else if (size >= 4 && p[0] == 0 && p[1] == 0 && p[2] == 0xfe 5128 && p[3] == 0xff && (flags == FIO_ALL || flags == FIO_UCS4)) 5129 { 5130 name = "ucs-4"; /* 00 00 FE FF */ 5131 len = 4; 5132 } 5133 5134 *lenp = len; 5135 return (char_u *)name; 5136 } 5137 5138 /* 5139 * Generate a BOM in "buf[4]" for encoding "name". 5140 * Return the length of the BOM (zero when no BOM). 5141 */ 5142 static int 5143 make_bom(buf, name) 5144 char_u *buf; 5145 char_u *name; 5146 { 5147 int flags; 5148 char_u *p; 5149 5150 flags = get_fio_flags(name); 5151 5152 /* Can't put a BOM in a non-Unicode file. */ 5153 if (flags == FIO_LATIN1 || flags == 0) 5154 return 0; 5155 5156 if (flags == FIO_UTF8) /* UTF-8 */ 5157 { 5158 buf[0] = 0xef; 5159 buf[1] = 0xbb; 5160 buf[2] = 0xbf; 5161 return 3; 5162 } 5163 p = buf; 5164 (void)ucs2bytes(0xfeff, &p, flags); 5165 return (int)(p - buf); 5166 } 5167 #endif 5168 5169 /* 5170 * Try to find a shortname by comparing the fullname with the current 5171 * directory. 5172 * Returns NULL if not shorter name possible, pointer into "full_path" 5173 * otherwise. 5174 */ 5175 char_u * 5176 shorten_fname(full_path, dir_name) 5177 char_u *full_path; 5178 char_u *dir_name; 5179 { 5180 int len; 5181 char_u *p; 5182 5183 if (full_path == NULL) 5184 return NULL; 5185 len = (int)STRLEN(dir_name); 5186 if (fnamencmp(dir_name, full_path, len) == 0) 5187 { 5188 p = full_path + len; 5189 #if defined(MSDOS) || defined(MSWIN) || defined(OS2) 5190 /* 5191 * MSDOS: when a file is in the root directory, dir_name will end in a 5192 * slash, since C: by itself does not define a specific dir. In this 5193 * case p may already be correct. <negri> 5194 */ 5195 if (!((len > 2) && (*(p - 2) == ':'))) 5196 #endif 5197 { 5198 if (vim_ispathsep(*p)) 5199 ++p; 5200 #ifndef VMS /* the path separator is always part of the path */ 5201 else 5202 p = NULL; 5203 #endif 5204 } 5205 } 5206 #if defined(MSDOS) || defined(MSWIN) || defined(OS2) 5207 /* 5208 * When using a file in the current drive, remove the drive name: 5209 * "A:\dir\file" -> "\dir\file". This helps when moving a session file on 5210 * a floppy from "A:\dir" to "B:\dir". 5211 */ 5212 else if (len > 3 5213 && TOUPPER_LOC(full_path[0]) == TOUPPER_LOC(dir_name[0]) 5214 && full_path[1] == ':' 5215 && vim_ispathsep(full_path[2])) 5216 p = full_path + 2; 5217 #endif 5218 else 5219 p = NULL; 5220 return p; 5221 } 5222 5223 /* 5224 * Shorten filenames for all buffers. 5225 * When "force" is TRUE: Use full path from now on for files currently being 5226 * edited, both for file name and swap file name. Try to shorten the file 5227 * names a bit, if safe to do so. 5228 * When "force" is FALSE: Only try to shorten absolute file names. 5229 * For buffers that have buftype "nofile" or "scratch": never change the file 5230 * name. 5231 */ 5232 void 5233 shorten_fnames(force) 5234 int force; 5235 { 5236 char_u dirname[MAXPATHL]; 5237 buf_T *buf; 5238 char_u *p; 5239 5240 mch_dirname(dirname, MAXPATHL); 5241 for (buf = firstbuf; buf != NULL; buf = buf->b_next) 5242 { 5243 if (buf->b_fname != NULL 5244 #ifdef FEAT_QUICKFIX 5245 && !bt_nofile(buf) 5246 #endif 5247 && !path_with_url(buf->b_fname) 5248 && (force 5249 || buf->b_sfname == NULL 5250 || mch_isFullName(buf->b_sfname))) 5251 { 5252 vim_free(buf->b_sfname); 5253 buf->b_sfname = NULL; 5254 p = shorten_fname(buf->b_ffname, dirname); 5255 if (p != NULL) 5256 { 5257 buf->b_sfname = vim_strsave(p); 5258 buf->b_fname = buf->b_sfname; 5259 } 5260 if (p == NULL || buf->b_fname == NULL) 5261 buf->b_fname = buf->b_ffname; 5262 } 5263 5264 /* Always make the swap file name a full path, a "nofile" buffer may 5265 * also have a swap file. */ 5266 mf_fullname(buf->b_ml.ml_mfp); 5267 } 5268 #ifdef FEAT_WINDOWS 5269 status_redraw_all(); 5270 #endif 5271 } 5272 5273 #if (defined(FEAT_DND) && defined(FEAT_GUI_GTK)) \ 5274 || defined(FEAT_GUI_MSWIN) \ 5275 || defined(FEAT_GUI_MAC) \ 5276 || defined(PROTO) 5277 /* 5278 * Shorten all filenames in "fnames[count]" by current directory. 5279 */ 5280 void 5281 shorten_filenames(fnames, count) 5282 char_u **fnames; 5283 int count; 5284 { 5285 int i; 5286 char_u dirname[MAXPATHL]; 5287 char_u *p; 5288 5289 if (fnames == NULL || count < 1) 5290 return; 5291 mch_dirname(dirname, sizeof(dirname)); 5292 for (i = 0; i < count; ++i) 5293 { 5294 if ((p = shorten_fname(fnames[i], dirname)) != NULL) 5295 { 5296 /* shorten_fname() returns pointer in given "fnames[i]". If free 5297 * "fnames[i]" first, "p" becomes invalid. So we need to copy 5298 * "p" first then free fnames[i]. */ 5299 p = vim_strsave(p); 5300 vim_free(fnames[i]); 5301 fnames[i] = p; 5302 } 5303 } 5304 } 5305 #endif 5306 5307 /* 5308 * add extention to file name - change path/fo.o.h to path/fo.o.h.ext or 5309 * fo_o_h.ext for MSDOS or when shortname option set. 5310 * 5311 * Assumed that fname is a valid name found in the filesystem we assure that 5312 * the return value is a different name and ends in 'ext'. 5313 * "ext" MUST be at most 4 characters long if it starts with a dot, 3 5314 * characters otherwise. 5315 * Space for the returned name is allocated, must be freed later. 5316 * Returns NULL when out of memory. 5317 */ 5318 char_u * 5319 modname(fname, ext, prepend_dot) 5320 char_u *fname, *ext; 5321 int prepend_dot; /* may prepend a '.' to file name */ 5322 { 5323 return buf_modname( 5324 #ifdef SHORT_FNAME 5325 TRUE, 5326 #else 5327 (curbuf->b_p_sn || curbuf->b_shortname), 5328 #endif 5329 fname, ext, prepend_dot); 5330 } 5331 5332 char_u * 5333 buf_modname(shortname, fname, ext, prepend_dot) 5334 int shortname; /* use 8.3 file name */ 5335 char_u *fname, *ext; 5336 int prepend_dot; /* may prepend a '.' to file name */ 5337 { 5338 char_u *retval; 5339 char_u *s; 5340 char_u *e; 5341 char_u *ptr; 5342 int fnamelen, extlen; 5343 5344 extlen = (int)STRLEN(ext); 5345 5346 /* 5347 * If there is no file name we must get the name of the current directory 5348 * (we need the full path in case :cd is used). 5349 */ 5350 if (fname == NULL || *fname == NUL) 5351 { 5352 retval = alloc((unsigned)(MAXPATHL + extlen + 3)); 5353 if (retval == NULL) 5354 return NULL; 5355 if (mch_dirname(retval, MAXPATHL) == FAIL || 5356 (fnamelen = (int)STRLEN(retval)) == 0) 5357 { 5358 vim_free(retval); 5359 return NULL; 5360 } 5361 if (!vim_ispathsep(retval[fnamelen - 1])) 5362 { 5363 retval[fnamelen++] = PATHSEP; 5364 retval[fnamelen] = NUL; 5365 } 5366 #ifndef SHORT_FNAME 5367 prepend_dot = FALSE; /* nothing to prepend a dot to */ 5368 #endif 5369 } 5370 else 5371 { 5372 fnamelen = (int)STRLEN(fname); 5373 retval = alloc((unsigned)(fnamelen + extlen + 3)); 5374 if (retval == NULL) 5375 return NULL; 5376 STRCPY(retval, fname); 5377 #ifdef VMS 5378 vms_remove_version(retval); /* we do not need versions here */ 5379 #endif 5380 } 5381 5382 /* 5383 * search backwards until we hit a '/', '\' or ':' replacing all '.' 5384 * by '_' for MSDOS or when shortname option set and ext starts with a dot. 5385 * Then truncate what is after the '/', '\' or ':' to 8 characters for 5386 * MSDOS and 26 characters for AMIGA, a lot more for UNIX. 5387 */ 5388 for (ptr = retval + fnamelen; ptr >= retval; ptr--) 5389 { 5390 #ifndef RISCOS 5391 if (*ext == '.' 5392 #ifdef USE_LONG_FNAME 5393 && (!USE_LONG_FNAME || shortname) 5394 #else 5395 # ifndef SHORT_FNAME 5396 && shortname 5397 # endif 5398 #endif 5399 ) 5400 if (*ptr == '.') /* replace '.' by '_' */ 5401 *ptr = '_'; 5402 #endif /* RISCOS */ 5403 if (vim_ispathsep(*ptr)) 5404 break; 5405 } 5406 ptr++; 5407 5408 /* the file name has at most BASENAMELEN characters. */ 5409 #ifndef SHORT_FNAME 5410 if (STRLEN(ptr) > (unsigned)BASENAMELEN) 5411 ptr[BASENAMELEN] = '\0'; 5412 #endif 5413 5414 s = ptr + STRLEN(ptr); 5415 5416 /* 5417 * For 8.3 file names we may have to reduce the length. 5418 */ 5419 #ifdef USE_LONG_FNAME 5420 if (!USE_LONG_FNAME || shortname) 5421 #else 5422 # ifndef SHORT_FNAME 5423 if (shortname) 5424 # endif 5425 #endif 5426 { 5427 /* 5428 * If there is no file name, or the file name ends in '/', and the 5429 * extension starts with '.', put a '_' before the dot, because just 5430 * ".ext" is invalid. 5431 */ 5432 if (fname == NULL || *fname == NUL 5433 || vim_ispathsep(fname[STRLEN(fname) - 1])) 5434 { 5435 #ifdef RISCOS 5436 if (*ext == '/') 5437 #else 5438 if (*ext == '.') 5439 #endif 5440 *s++ = '_'; 5441 } 5442 /* 5443 * If the extension starts with '.', truncate the base name at 8 5444 * characters 5445 */ 5446 #ifdef RISCOS 5447 /* We normally use '/', but swap files are '_' */ 5448 else if (*ext == '/' || *ext == '_') 5449 #else 5450 else if (*ext == '.') 5451 #endif 5452 { 5453 if (s - ptr > (size_t)8) 5454 { 5455 s = ptr + 8; 5456 *s = '\0'; 5457 } 5458 } 5459 /* 5460 * If the extension doesn't start with '.', and the file name 5461 * doesn't have an extension yet, append a '.' 5462 */ 5463 #ifdef RISCOS 5464 else if ((e = vim_strchr(ptr, '/')) == NULL) 5465 *s++ = '/'; 5466 #else 5467 else if ((e = vim_strchr(ptr, '.')) == NULL) 5468 *s++ = '.'; 5469 #endif 5470 /* 5471 * If the extension doesn't start with '.', and there already is an 5472 * extension, it may need to be tructated 5473 */ 5474 else if ((int)STRLEN(e) + extlen > 4) 5475 s = e + 4 - extlen; 5476 } 5477 #if defined(OS2) || defined(USE_LONG_FNAME) || defined(WIN3264) 5478 /* 5479 * If there is no file name, and the extension starts with '.', put a 5480 * '_' before the dot, because just ".ext" may be invalid if it's on a 5481 * FAT partition, and on HPFS it doesn't matter. 5482 */ 5483 else if ((fname == NULL || *fname == NUL) && *ext == '.') 5484 *s++ = '_'; 5485 #endif 5486 5487 /* 5488 * Append the extention. 5489 * ext can start with '.' and cannot exceed 3 more characters. 5490 */ 5491 STRCPY(s, ext); 5492 5493 #ifndef SHORT_FNAME 5494 /* 5495 * Prepend the dot. 5496 */ 5497 if (prepend_dot && !shortname && *(e = gettail(retval)) != 5498 #ifdef RISCOS 5499 '/' 5500 #else 5501 '.' 5502 #endif 5503 #ifdef USE_LONG_FNAME 5504 && USE_LONG_FNAME 5505 #endif 5506 ) 5507 { 5508 mch_memmove(e + 1, e, STRLEN(e) + 1); 5509 #ifdef RISCOS 5510 *e = '/'; 5511 #else 5512 *e = '.'; 5513 #endif 5514 } 5515 #endif 5516 5517 /* 5518 * Check that, after appending the extension, the file name is really 5519 * different. 5520 */ 5521 if (fname != NULL && STRCMP(fname, retval) == 0) 5522 { 5523 /* we search for a character that can be replaced by '_' */ 5524 while (--s >= ptr) 5525 { 5526 if (*s != '_') 5527 { 5528 *s = '_'; 5529 break; 5530 } 5531 } 5532 if (s < ptr) /* fname was "________.<ext>", how tricky! */ 5533 *ptr = 'v'; 5534 } 5535 return retval; 5536 } 5537 5538 /* 5539 * Like fgets(), but if the file line is too long, it is truncated and the 5540 * rest of the line is thrown away. Returns TRUE for end-of-file. 5541 */ 5542 int 5543 vim_fgets(buf, size, fp) 5544 char_u *buf; 5545 int size; 5546 FILE *fp; 5547 { 5548 char *eof; 5549 #define FGETS_SIZE 200 5550 char tbuf[FGETS_SIZE]; 5551 5552 buf[size - 2] = NUL; 5553 #ifdef USE_CR 5554 eof = fgets_cr((char *)buf, size, fp); 5555 #else 5556 eof = fgets((char *)buf, size, fp); 5557 #endif 5558 if (buf[size - 2] != NUL && buf[size - 2] != '\n') 5559 { 5560 buf[size - 1] = NUL; /* Truncate the line */ 5561 5562 /* Now throw away the rest of the line: */ 5563 do 5564 { 5565 tbuf[FGETS_SIZE - 2] = NUL; 5566 #ifdef USE_CR 5567 fgets_cr((char *)tbuf, FGETS_SIZE, fp); 5568 #else 5569 fgets((char *)tbuf, FGETS_SIZE, fp); 5570 #endif 5571 } while (tbuf[FGETS_SIZE - 2] != NUL && tbuf[FGETS_SIZE - 2] != '\n'); 5572 } 5573 return (eof == NULL); 5574 } 5575 5576 #if defined(USE_CR) || defined(PROTO) 5577 /* 5578 * Like vim_fgets(), but accept any line terminator: CR, CR-LF or LF. 5579 * Returns TRUE for end-of-file. 5580 * Only used for the Mac, because it's much slower than vim_fgets(). 5581 */ 5582 int 5583 tag_fgets(buf, size, fp) 5584 char_u *buf; 5585 int size; 5586 FILE *fp; 5587 { 5588 int i = 0; 5589 int c; 5590 int eof = FALSE; 5591 5592 for (;;) 5593 { 5594 c = fgetc(fp); 5595 if (c == EOF) 5596 { 5597 eof = TRUE; 5598 break; 5599 } 5600 if (c == '\r') 5601 { 5602 /* Always store a NL for end-of-line. */ 5603 if (i < size - 1) 5604 buf[i++] = '\n'; 5605 c = fgetc(fp); 5606 if (c != '\n') /* Macintosh format: single CR. */ 5607 ungetc(c, fp); 5608 break; 5609 } 5610 if (i < size - 1) 5611 buf[i++] = c; 5612 if (c == '\n') 5613 break; 5614 } 5615 buf[i] = NUL; 5616 return eof; 5617 } 5618 #endif 5619 5620 /* 5621 * rename() only works if both files are on the same file system, this 5622 * function will (attempts to?) copy the file across if rename fails -- webb 5623 * Return -1 for failure, 0 for success. 5624 */ 5625 int 5626 vim_rename(from, to) 5627 char_u *from; 5628 char_u *to; 5629 { 5630 int fd_in; 5631 int fd_out; 5632 int n; 5633 char *errmsg = NULL; 5634 char *buffer; 5635 #ifdef AMIGA 5636 BPTR flock; 5637 #endif 5638 struct stat st; 5639 5640 /* 5641 * When the names are identical, there is nothing to do. 5642 */ 5643 if (fnamecmp(from, to) == 0) 5644 return 0; 5645 5646 /* 5647 * Fail if the "from" file doesn't exist. Avoids that "to" is deleted. 5648 */ 5649 if (mch_stat((char *)from, &st) < 0) 5650 return -1; 5651 5652 /* 5653 * Delete the "to" file, this is required on some systems to make the 5654 * mch_rename() work, on other systems it makes sure that we don't have 5655 * two files when the mch_rename() fails. 5656 */ 5657 5658 #ifdef AMIGA 5659 /* 5660 * With MSDOS-compatible filesystems (crossdos, messydos) it is possible 5661 * that the name of the "to" file is the same as the "from" file, even 5662 * though the names are different. To avoid the chance of accidently 5663 * deleting the "from" file (horror!) we lock it during the remove. 5664 * 5665 * When used for making a backup before writing the file: This should not 5666 * happen with ":w", because startscript() should detect this problem and 5667 * set buf->b_shortname, causing modname() to return a correct ".bak" file 5668 * name. This problem does exist with ":w filename", but then the 5669 * original file will be somewhere else so the backup isn't really 5670 * important. If autoscripting is off the rename may fail. 5671 */ 5672 flock = Lock((UBYTE *)from, (long)ACCESS_READ); 5673 #endif 5674 mch_remove(to); 5675 #ifdef AMIGA 5676 if (flock) 5677 UnLock(flock); 5678 #endif 5679 5680 /* 5681 * First try a normal rename, return if it works. 5682 */ 5683 if (mch_rename((char *)from, (char *)to) == 0) 5684 return 0; 5685 5686 /* 5687 * Rename() failed, try copying the file. 5688 */ 5689 fd_in = mch_open((char *)from, O_RDONLY|O_EXTRA, 0); 5690 if (fd_in == -1) 5691 return -1; 5692 fd_out = mch_open((char *)to, O_CREAT|O_EXCL|O_WRONLY|O_EXTRA, 0666); 5693 if (fd_out == -1) 5694 { 5695 close(fd_in); 5696 return -1; 5697 } 5698 5699 buffer = (char *)alloc(BUFSIZE); 5700 if (buffer == NULL) 5701 { 5702 close(fd_in); 5703 close(fd_out); 5704 return -1; 5705 } 5706 5707 while ((n = vim_read(fd_in, buffer, BUFSIZE)) > 0) 5708 if (vim_write(fd_out, buffer, n) != n) 5709 { 5710 errmsg = _("E208: Error writing to \"%s\""); 5711 break; 5712 } 5713 5714 vim_free(buffer); 5715 close(fd_in); 5716 if (close(fd_out) < 0) 5717 errmsg = _("E209: Error closing \"%s\""); 5718 if (n < 0) 5719 { 5720 errmsg = _("E210: Error reading \"%s\""); 5721 to = from; 5722 } 5723 if (errmsg != NULL) 5724 { 5725 EMSG2(errmsg, to); 5726 return -1; 5727 } 5728 mch_remove(from); 5729 return 0; 5730 } 5731 5732 static int already_warned = FALSE; 5733 5734 /* 5735 * Check if any not hidden buffer has been changed. 5736 * Postpone the check if there are characters in the stuff buffer, a global 5737 * command is being executed, a mapping is being executed or an autocommand is 5738 * busy. 5739 * Returns TRUE if some message was written (screen should be redrawn and 5740 * cursor positioned). 5741 */ 5742 int 5743 check_timestamps(focus) 5744 int focus; /* called for GUI focus event */ 5745 { 5746 buf_T *buf; 5747 int didit = 0; 5748 int n; 5749 5750 /* Don't check timestamps while system() or another low-level function may 5751 * cause us to lose and gain focus. */ 5752 if (no_check_timestamps > 0) 5753 return FALSE; 5754 5755 /* Avoid doing a check twice. The OK/Reload dialog can cause a focus 5756 * event and we would keep on checking if the file is steadily growing. 5757 * Do check again after typing something. */ 5758 if (focus && did_check_timestamps) 5759 { 5760 need_check_timestamps = TRUE; 5761 return FALSE; 5762 } 5763 5764 if (!stuff_empty() || global_busy || !typebuf_typed() 5765 #ifdef FEAT_AUTOCMD 5766 || autocmd_busy 5767 #endif 5768 ) 5769 need_check_timestamps = TRUE; /* check later */ 5770 else 5771 { 5772 ++no_wait_return; 5773 did_check_timestamps = TRUE; 5774 already_warned = FALSE; 5775 for (buf = firstbuf; buf != NULL; ) 5776 { 5777 /* Only check buffers in a window. */ 5778 if (buf->b_nwindows > 0) 5779 { 5780 n = buf_check_timestamp(buf, focus); 5781 if (didit < n) 5782 didit = n; 5783 if (n > 0 && !buf_valid(buf)) 5784 { 5785 /* Autocommands have removed the buffer, start at the 5786 * first one again. */ 5787 buf = firstbuf; 5788 continue; 5789 } 5790 } 5791 buf = buf->b_next; 5792 } 5793 --no_wait_return; 5794 need_check_timestamps = FALSE; 5795 if (need_wait_return && didit == 2) 5796 { 5797 /* make sure msg isn't overwritten */ 5798 msg_puts((char_u *)"\n"); 5799 out_flush(); 5800 } 5801 } 5802 return didit; 5803 } 5804 5805 /* 5806 * Move all the lines from buffer "frombuf" to buffer "tobuf". 5807 * Return OK or FAIL. When FAIL "tobuf" is incomplete and/or "frombuf" is not 5808 * empty. 5809 */ 5810 static int 5811 move_lines(frombuf, tobuf) 5812 buf_T *frombuf; 5813 buf_T *tobuf; 5814 { 5815 buf_T *tbuf = curbuf; 5816 int retval = OK; 5817 linenr_T lnum; 5818 char_u *p; 5819 5820 /* Copy the lines in "frombuf" to "tobuf". */ 5821 curbuf = tobuf; 5822 for (lnum = 1; lnum <= frombuf->b_ml.ml_line_count; ++lnum) 5823 { 5824 p = vim_strsave(ml_get_buf(frombuf, lnum, FALSE)); 5825 if (p == NULL || ml_append(lnum - 1, p, 0, FALSE) == FAIL) 5826 { 5827 vim_free(p); 5828 retval = FAIL; 5829 break; 5830 } 5831 vim_free(p); 5832 } 5833 5834 /* Delete all the lines in "frombuf". */ 5835 if (retval != FAIL) 5836 { 5837 curbuf = frombuf; 5838 while (!bufempty()) 5839 if (ml_delete(curbuf->b_ml.ml_line_count, FALSE) == FAIL) 5840 { 5841 /* Oops! We could try putting back the saved lines, but that 5842 * might fail again... */ 5843 retval = FAIL; 5844 break; 5845 } 5846 } 5847 5848 curbuf = tbuf; 5849 return retval; 5850 } 5851 5852 /* 5853 * Check if buffer "buf" has been changed. 5854 * Also check if the file for a new buffer unexpectedly appeared. 5855 * return 1 if a changed buffer was found. 5856 * return 2 if a message has been displayed. 5857 * return 0 otherwise. 5858 */ 5859 /*ARGSUSED*/ 5860 int 5861 buf_check_timestamp(buf, focus) 5862 buf_T *buf; 5863 int focus; /* called for GUI focus event */ 5864 { 5865 struct stat st; 5866 int stat_res; 5867 int retval = 0; 5868 char_u *path; 5869 char_u *tbuf; 5870 char *mesg = NULL; 5871 char *mesg2; 5872 int helpmesg = FALSE; 5873 int reload = FALSE; 5874 #if defined(FEAT_CON_DIALOG) || defined(FEAT_GUI_DIALOG) 5875 int can_reload = FALSE; 5876 #endif 5877 size_t orig_size = buf->b_orig_size; 5878 int orig_mode = buf->b_orig_mode; 5879 #ifdef FEAT_GUI 5880 int save_mouse_correct = need_mouse_correct; 5881 #endif 5882 #ifdef FEAT_AUTOCMD 5883 static int busy = FALSE; 5884 #endif 5885 5886 /* If there is no file name, the buffer is not loaded, 'buftype' is 5887 * set, we are in the middle of a save or being called recursively: ignore 5888 * this buffer. */ 5889 if (buf->b_ffname == NULL 5890 || buf->b_ml.ml_mfp == NULL 5891 #if defined(FEAT_QUICKFIX) 5892 || *buf->b_p_bt != NUL 5893 #endif 5894 || buf->b_saving 5895 #ifdef FEAT_AUTOCMD 5896 || busy 5897 #endif 5898 ) 5899 return 0; 5900 5901 if ( !(buf->b_flags & BF_NOTEDITED) 5902 && buf->b_mtime != 0 5903 && ((stat_res = mch_stat((char *)buf->b_ffname, &st)) < 0 5904 || time_differs((long)st.st_mtime, buf->b_mtime) 5905 #ifdef HAVE_ST_MODE 5906 || (int)st.st_mode != buf->b_orig_mode 5907 #else 5908 || mch_getperm(buf->b_ffname) != buf->b_orig_mode 5909 #endif 5910 )) 5911 { 5912 retval = 1; 5913 5914 /* set b_mtime to stop further warnings */ 5915 if (stat_res < 0) 5916 { 5917 buf->b_mtime = 0; 5918 buf->b_orig_size = 0; 5919 buf->b_orig_mode = 0; 5920 } 5921 else 5922 buf_store_time(buf, &st, buf->b_ffname); 5923 5924 /* Don't do anything for a directory. Might contain the file 5925 * explorer. */ 5926 if (mch_isdir(buf->b_fname)) 5927 ; 5928 5929 /* 5930 * If 'autoread' is set, the buffer has no changes and the file still 5931 * exists, reload the buffer. Use the buffer-local option value if it 5932 * was set, the global option value otherwise. 5933 */ 5934 else if ((buf->b_p_ar >= 0 ? buf->b_p_ar : p_ar) 5935 && !bufIsChanged(buf) && stat_res >= 0) 5936 reload = TRUE; 5937 else 5938 { 5939 #ifdef FEAT_AUTOCMD 5940 int n; 5941 5942 /* 5943 * Only give the warning if there are no FileChangedShell 5944 * autocommands. 5945 * Avoid being called recursively by setting "busy". 5946 */ 5947 busy = TRUE; 5948 n = apply_autocmds(EVENT_FILECHANGEDSHELL, 5949 buf->b_fname, buf->b_fname, FALSE, buf); 5950 busy = FALSE; 5951 if (n) 5952 { 5953 if (!buf_valid(buf)) 5954 EMSG(_("E246: FileChangedShell autocommand deleted buffer")); 5955 return 2; 5956 } 5957 else 5958 #endif 5959 { 5960 if (stat_res < 0) 5961 mesg = _("E211: Warning: File \"%s\" no longer available"); 5962 else 5963 { 5964 helpmesg = TRUE; 5965 #if defined(FEAT_CON_DIALOG) || defined(FEAT_GUI_DIALOG) 5966 can_reload = TRUE; 5967 #endif 5968 /* 5969 * Check if the file contents really changed to avoid 5970 * giving a warning when only the timestamp was set (e.g., 5971 * checked out of CVS). Always warn when the buffer was 5972 * changed. 5973 */ 5974 if (bufIsChanged(buf)) 5975 mesg = _("W12: Warning: File \"%s\" has changed and the buffer was changed in Vim as well"); 5976 else if (orig_size != buf->b_orig_size 5977 || buf_contents_changed(buf)) 5978 mesg = _("W11: Warning: File \"%s\" has changed since editing started"); 5979 else if (orig_mode != buf->b_orig_mode) 5980 mesg = _("W16: Warning: Mode of file \"%s\" has changed since editing started"); 5981 } 5982 } 5983 } 5984 5985 } 5986 else if ((buf->b_flags & BF_NEW) && !(buf->b_flags & BF_NEW_W) 5987 && vim_fexists(buf->b_ffname)) 5988 { 5989 retval = 1; 5990 mesg = _("W13: Warning: File \"%s\" has been created after editing started"); 5991 buf->b_flags |= BF_NEW_W; 5992 #if defined(FEAT_CON_DIALOG) || defined(FEAT_GUI_DIALOG) 5993 can_reload = TRUE; 5994 #endif 5995 } 5996 5997 if (mesg != NULL) 5998 { 5999 path = home_replace_save(buf, buf->b_fname); 6000 if (path != NULL) 6001 { 6002 if (helpmesg) 6003 mesg2 = _("See \":help W11\" for more info."); 6004 else 6005 mesg2 = ""; 6006 tbuf = alloc((unsigned)(STRLEN(path) + STRLEN(mesg) 6007 + STRLEN(mesg2) + 2)); 6008 sprintf((char *)tbuf, mesg, path); 6009 #if defined(FEAT_CON_DIALOG) || defined(FEAT_GUI_DIALOG) 6010 if (can_reload) 6011 { 6012 if (*mesg2 != NUL) 6013 { 6014 STRCAT(tbuf, "\n"); 6015 STRCAT(tbuf, mesg2); 6016 } 6017 if (do_dialog(VIM_WARNING, (char_u *)_("Warning"), tbuf, 6018 (char_u *)_("&OK\n&Load File"), 1, NULL) == 2) 6019 reload = TRUE; 6020 } 6021 else 6022 #endif 6023 if (State > NORMAL_BUSY || (State & CMDLINE) || already_warned) 6024 { 6025 if (*mesg2 != NUL) 6026 { 6027 STRCAT(tbuf, "; "); 6028 STRCAT(tbuf, mesg2); 6029 } 6030 EMSG(tbuf); 6031 retval = 2; 6032 } 6033 else 6034 { 6035 # ifdef FEAT_AUTOCMD 6036 if (!autocmd_busy) 6037 # endif 6038 { 6039 msg_start(); 6040 msg_puts_attr(tbuf, hl_attr(HLF_E) + MSG_HIST); 6041 if (*mesg2 != NUL) 6042 msg_puts_attr((char_u *)mesg2, 6043 hl_attr(HLF_W) + MSG_HIST); 6044 msg_clr_eos(); 6045 (void)msg_end(); 6046 if (emsg_silent == 0) 6047 { 6048 out_flush(); 6049 # ifdef FEAT_GUI 6050 if (!focus) 6051 # endif 6052 /* give the user some time to think about it */ 6053 ui_delay(1000L, TRUE); 6054 6055 /* don't redraw and erase the message */ 6056 redraw_cmdline = FALSE; 6057 } 6058 } 6059 already_warned = TRUE; 6060 } 6061 6062 vim_free(path); 6063 vim_free(tbuf); 6064 } 6065 } 6066 6067 if (reload) 6068 { 6069 exarg_T ea; 6070 pos_T old_cursor; 6071 linenr_T old_topline; 6072 int old_ro = buf->b_p_ro; 6073 buf_T *savebuf; 6074 int saved = OK; 6075 #ifdef FEAT_AUTOCMD 6076 aco_save_T aco; 6077 6078 /* set curwin/curbuf for "buf" and save some things */ 6079 aucmd_prepbuf(&aco, buf); 6080 #else 6081 buf_T *save_curbuf = curbuf; 6082 6083 curbuf = buf; 6084 curwin->w_buffer = buf; 6085 #endif 6086 6087 /* We only want to read the text from the file, not reset the syntax 6088 * highlighting, clear marks, diff status, etc. Force the fileformat 6089 * and encoding to be the same. */ 6090 if (prep_exarg(&ea, buf) == OK) 6091 { 6092 old_cursor = curwin->w_cursor; 6093 old_topline = curwin->w_topline; 6094 6095 /* 6096 * To behave like when a new file is edited (matters for 6097 * BufReadPost autocommands) we first need to delete the current 6098 * buffer contents. But if reading the file fails we should keep 6099 * the old contents. Can't use memory only, the file might be 6100 * too big. Use a hidden buffer to move the buffer contents to. 6101 */ 6102 if (bufempty()) 6103 savebuf = NULL; 6104 else 6105 { 6106 /* Allocate a buffer without putting it in the buffer list. */ 6107 savebuf = buflist_new(NULL, NULL, (linenr_T)1, BLN_DUMMY); 6108 if (savebuf != NULL) 6109 { 6110 /* Open the memline. */ 6111 curbuf = savebuf; 6112 curwin->w_buffer = savebuf; 6113 saved = ml_open(); 6114 curbuf = buf; 6115 curwin->w_buffer = buf; 6116 } 6117 if (savebuf == NULL || saved == FAIL 6118 || move_lines(buf, savebuf) == FAIL) 6119 { 6120 EMSG2(_("E462: Could not prepare for reloading \"%s\""), 6121 buf->b_fname); 6122 saved = FAIL; 6123 } 6124 } 6125 6126 if (saved == OK) 6127 { 6128 curbuf->b_flags |= BF_CHECK_RO; /* check for RO again */ 6129 #ifdef FEAT_AUTOCMD 6130 keep_filetype = TRUE; /* don't detect 'filetype' */ 6131 #endif 6132 if (readfile(buf->b_ffname, buf->b_fname, (linenr_T)0, 6133 (linenr_T)0, 6134 (linenr_T)MAXLNUM, &ea, READ_NEW) == FAIL) 6135 { 6136 #if defined(FEAT_AUTOCMD) && defined(FEAT_EVAL) 6137 if (!aborting()) 6138 #endif 6139 EMSG2(_("E321: Could not reload \"%s\""), buf->b_fname); 6140 if (savebuf != NULL) 6141 { 6142 /* Put the text back from the save buffer. First 6143 * delete any lines that readfile() added. */ 6144 while (!bufempty()) 6145 if (ml_delete(curbuf->b_ml.ml_line_count, FALSE) 6146 == FAIL) 6147 break; 6148 (void)move_lines(savebuf, buf); 6149 } 6150 } 6151 else 6152 { 6153 /* Mark the buffer as unmodified and free undo info. */ 6154 unchanged(buf, TRUE); 6155 u_blockfree(buf); 6156 u_clearall(buf); 6157 } 6158 } 6159 vim_free(ea.cmd); 6160 6161 if (savebuf != NULL) 6162 wipe_buffer(savebuf, FALSE); 6163 6164 #ifdef FEAT_DIFF 6165 /* Invalidate diff info if necessary. */ 6166 diff_invalidate(); 6167 #endif 6168 6169 /* Restore the topline and cursor position and check it (lines may 6170 * have been removed). */ 6171 if (old_topline > curbuf->b_ml.ml_line_count) 6172 curwin->w_topline = curbuf->b_ml.ml_line_count; 6173 else 6174 curwin->w_topline = old_topline; 6175 curwin->w_cursor = old_cursor; 6176 check_cursor(); 6177 update_topline(); 6178 #ifdef FEAT_AUTOCMD 6179 keep_filetype = FALSE; 6180 #endif 6181 #ifdef FEAT_FOLDING 6182 { 6183 win_T *wp; 6184 6185 /* Update folds unless they are defined manually. */ 6186 FOR_ALL_WINDOWS(wp) 6187 if (wp->w_buffer == curwin->w_buffer 6188 && !foldmethodIsManual(wp)) 6189 foldUpdateAll(wp); 6190 } 6191 #endif 6192 /* If the mode didn't change and 'readonly' was set, keep the old 6193 * value; the user probably used the ":view" command. But don't 6194 * reset it, might have had a read error. */ 6195 if (orig_mode == curbuf->b_orig_mode) 6196 curbuf->b_p_ro |= old_ro; 6197 } 6198 6199 #ifdef FEAT_AUTOCMD 6200 /* restore curwin/curbuf and a few other things */ 6201 aucmd_restbuf(&aco); 6202 /* Careful: autocommands may have made "buf" invalid! */ 6203 #else 6204 curwin->w_buffer = save_curbuf; 6205 curbuf = save_curbuf; 6206 #endif 6207 } 6208 6209 #ifdef FEAT_GUI 6210 /* restore this in case an autocommand has set it; it would break 6211 * 'mousefocus' */ 6212 need_mouse_correct = save_mouse_correct; 6213 #endif 6214 6215 return retval; 6216 } 6217 6218 /*ARGSUSED*/ 6219 void 6220 buf_store_time(buf, st, fname) 6221 buf_T *buf; 6222 struct stat *st; 6223 char_u *fname; 6224 { 6225 buf->b_mtime = (long)st->st_mtime; 6226 buf->b_orig_size = (size_t)st->st_size; 6227 #ifdef HAVE_ST_MODE 6228 buf->b_orig_mode = (int)st->st_mode; 6229 #else 6230 buf->b_orig_mode = mch_getperm(fname); 6231 #endif 6232 } 6233 6234 /* 6235 * Adjust the line with missing eol, used for the next write. 6236 * Used for do_filter(), when the input lines for the filter are deleted. 6237 */ 6238 void 6239 write_lnum_adjust(offset) 6240 linenr_T offset; 6241 { 6242 if (write_no_eol_lnum) /* only if there is a missing eol */ 6243 write_no_eol_lnum += offset; 6244 } 6245 6246 #if defined(TEMPDIRNAMES) || defined(PROTO) 6247 static long temp_count = 0; /* Temp filename counter. */ 6248 6249 /* 6250 * Delete the temp directory and all files it contains. 6251 */ 6252 void 6253 vim_deltempdir() 6254 { 6255 char_u **files; 6256 int file_count; 6257 int i; 6258 6259 if (vim_tempdir != NULL) 6260 { 6261 sprintf((char *)NameBuff, "%s*", vim_tempdir); 6262 if (gen_expand_wildcards(1, &NameBuff, &file_count, &files, 6263 EW_DIR|EW_FILE|EW_SILENT) == OK) 6264 { 6265 for (i = 0; i < file_count; ++i) 6266 mch_remove(files[i]); 6267 FreeWild(file_count, files); 6268 } 6269 gettail(NameBuff)[-1] = NUL; 6270 (void)mch_rmdir(NameBuff); 6271 6272 vim_free(vim_tempdir); 6273 vim_tempdir = NULL; 6274 } 6275 } 6276 #endif 6277 6278 /* 6279 * vim_tempname(): Return a unique name that can be used for a temp file. 6280 * 6281 * The temp file is NOT created. 6282 * 6283 * The returned pointer is to allocated memory. 6284 * The returned pointer is NULL if no valid name was found. 6285 */ 6286 /*ARGSUSED*/ 6287 char_u * 6288 vim_tempname(extra_char) 6289 int extra_char; /* character to use in the name instead of '?' */ 6290 { 6291 #ifdef USE_TMPNAM 6292 char_u itmp[L_tmpnam]; /* use tmpnam() */ 6293 #else 6294 char_u itmp[TEMPNAMELEN]; 6295 #endif 6296 6297 #ifdef TEMPDIRNAMES 6298 static char *(tempdirs[]) = {TEMPDIRNAMES}; 6299 int i; 6300 long nr; 6301 long off; 6302 # ifndef EEXIST 6303 struct stat st; 6304 # endif 6305 6306 /* 6307 * This will create a directory for private use by this instance of Vim. 6308 * This is done once, and the same directory is used for all temp files. 6309 * This method avoids security problems because of symlink attacks et al. 6310 * It's also a bit faster, because we only need to check for an existing 6311 * file when creating the directory and not for each temp file. 6312 */ 6313 if (vim_tempdir == NULL) 6314 { 6315 /* 6316 * Try the entries in TEMPDIRNAMES to create the temp directory. 6317 */ 6318 for (i = 0; i < sizeof(tempdirs) / sizeof(char *); ++i) 6319 { 6320 /* expand $TMP, leave room for "/v1100000/999999999" */ 6321 expand_env((char_u *)tempdirs[i], itmp, TEMPNAMELEN - 20); 6322 if (mch_isdir(itmp)) /* directory exists */ 6323 { 6324 # ifdef __EMX__ 6325 /* If $TMP contains a forward slash (perhaps using bash or 6326 * tcsh), don't add a backslash, use a forward slash! 6327 * Adding 2 backslashes didn't work. */ 6328 if (vim_strchr(itmp, '/') != NULL) 6329 STRCAT(itmp, "/"); 6330 else 6331 # endif 6332 add_pathsep(itmp); 6333 6334 /* Get an arbitrary number of up to 6 digits. When it's 6335 * unlikely that it already exists it will be faster, 6336 * otherwise it doesn't matter. The use of mkdir() avoids any 6337 * security problems because of the predictable number. */ 6338 nr = (mch_get_pid() + (long)time(NULL)) % 1000000L; 6339 6340 /* Try up to 10000 different values until we find a name that 6341 * doesn't exist. */ 6342 for (off = 0; off < 10000L; ++off) 6343 { 6344 int r; 6345 #if defined(UNIX) || defined(VMS) 6346 mode_t umask_save; 6347 #endif 6348 6349 sprintf((char *)itmp + STRLEN(itmp), "v%ld", nr + off); 6350 # ifndef EEXIST 6351 /* If mkdir() does not set errno to EEXIST, check for 6352 * existing file here. There is a race condition then, 6353 * although it's fail-safe. */ 6354 if (mch_stat((char *)itmp, &st) >= 0) 6355 continue; 6356 # endif 6357 #if defined(UNIX) || defined(VMS) 6358 /* Make sure the umask doesn't remove the executable bit. 6359 * "repl" has been reported to use "177". */ 6360 umask_save = umask(077); 6361 #endif 6362 r = vim_mkdir(itmp, 0700); 6363 #if defined(UNIX) || defined(VMS) 6364 (void)umask(umask_save); 6365 #endif 6366 if (r == 0) 6367 { 6368 char_u *buf; 6369 6370 /* Directory was created, use this name. 6371 * Expand to full path; When using the current 6372 * directory a ":cd" would confuse us. */ 6373 buf = alloc((unsigned)MAXPATHL + 1); 6374 if (buf != NULL) 6375 { 6376 if (vim_FullName(itmp, buf, MAXPATHL, FALSE) 6377 == FAIL) 6378 STRCPY(buf, itmp); 6379 # ifdef __EMX__ 6380 if (vim_strchr(buf, '/') != NULL) 6381 STRCAT(buf, "/"); 6382 else 6383 # endif 6384 add_pathsep(buf); 6385 vim_tempdir = vim_strsave(buf); 6386 vim_free(buf); 6387 } 6388 break; 6389 } 6390 # ifdef EEXIST 6391 /* If the mkdir() didn't fail because the file/dir exists, 6392 * we probably can't create any dir here, try another 6393 * place. */ 6394 if (errno != EEXIST) 6395 # endif 6396 break; 6397 } 6398 if (vim_tempdir != NULL) 6399 break; 6400 } 6401 } 6402 } 6403 6404 if (vim_tempdir != NULL) 6405 { 6406 /* There is no need to check if the file exists, because we own the 6407 * directory and nobody else creates a file in it. */ 6408 sprintf((char *)itmp, "%s%ld", vim_tempdir, temp_count++); 6409 return vim_strsave(itmp); 6410 } 6411 6412 return NULL; 6413 6414 #else /* TEMPDIRNAMES */ 6415 6416 # ifdef WIN3264 6417 char szTempFile[_MAX_PATH + 1]; 6418 char buf4[4]; 6419 char_u *retval; 6420 char_u *p; 6421 6422 STRCPY(itmp, ""); 6423 if (GetTempPath(_MAX_PATH, szTempFile) == 0) 6424 szTempFile[0] = NUL; /* GetTempPath() failed, use current dir */ 6425 strcpy(buf4, "VIM"); 6426 buf4[2] = extra_char; /* make it "VIa", "VIb", etc. */ 6427 if (GetTempFileName(szTempFile, buf4, 0, itmp) == 0) 6428 return NULL; 6429 /* GetTempFileName() will create the file, we don't want that */ 6430 (void)DeleteFile(itmp); 6431 6432 /* Backslashes in a temp file name cause problems when filtering with 6433 * "sh". NOTE: This also checks 'shellcmdflag' to help those people who 6434 * didn't set 'shellslash'. */ 6435 retval = vim_strsave(itmp); 6436 if (*p_shcf == '-' || p_ssl) 6437 for (p = retval; *p; ++p) 6438 if (*p == '\\') 6439 *p = '/'; 6440 return retval; 6441 6442 # else /* WIN3264 */ 6443 6444 # ifdef USE_TMPNAM 6445 /* tmpnam() will make its own name */ 6446 if (*tmpnam((char *)itmp) == NUL) 6447 return NULL; 6448 # else 6449 char_u *p; 6450 6451 # ifdef VMS_TEMPNAM 6452 /* mktemp() is not working on VMS. It seems to be 6453 * a do-nothing function. Therefore we use tempnam(). 6454 */ 6455 sprintf((char *)itmp, "VIM%c", extra_char); 6456 p = (char_u *)tempnam("tmp:", (char *)itmp); 6457 if (p != NULL) 6458 { 6459 /* VMS will use '.LOG' if we don't explicitly specify an extension, 6460 * and VIM will then be unable to find the file later */ 6461 STRCPY(itmp, p); 6462 STRCAT(itmp, ".txt"); 6463 free(p); 6464 } 6465 else 6466 return NULL; 6467 # else 6468 STRCPY(itmp, TEMPNAME); 6469 if ((p = vim_strchr(itmp, '?')) != NULL) 6470 *p = extra_char; 6471 if (mktemp((char *)itmp) == NULL) 6472 return NULL; 6473 # endif 6474 # endif 6475 6476 return vim_strsave(itmp); 6477 # endif /* WIN3264 */ 6478 #endif /* TEMPDIRNAMES */ 6479 } 6480 6481 #if defined(BACKSLASH_IN_FILENAME) || defined(PROTO) 6482 /* 6483 * Convert all backslashes in fname to forward slashes in-place. 6484 */ 6485 void 6486 forward_slash(fname) 6487 char_u *fname; 6488 { 6489 char_u *p; 6490 6491 for (p = fname; *p != NUL; ++p) 6492 # ifdef FEAT_MBYTE 6493 /* The Big5 encoding can have '\' in the trail byte. */ 6494 if (enc_dbcs != 0 && (*mb_ptr2len_check)(p) > 1) 6495 ++p; 6496 else 6497 # endif 6498 if (*p == '\\') 6499 *p = '/'; 6500 } 6501 #endif 6502 6503 6504 /* 6505 * Code for automatic commands. 6506 * 6507 * Only included when "FEAT_AUTOCMD" has been defined. 6508 */ 6509 6510 #if defined(FEAT_AUTOCMD) || defined(PROTO) 6511 6512 /* 6513 * The autocommands are stored in a list for each event. 6514 * Autocommands for the same pattern, that are consecutive, are joined 6515 * together, to avoid having to match the pattern too often. 6516 * The result is an array of Autopat lists, which point to AutoCmd lists: 6517 * 6518 * first_autopat[0] --> Autopat.next --> Autopat.next --> NULL 6519 * Autopat.cmds Autopat.cmds 6520 * | | 6521 * V V 6522 * AutoCmd.next AutoCmd.next 6523 * | | 6524 * V V 6525 * AutoCmd.next NULL 6526 * | 6527 * V 6528 * NULL 6529 * 6530 * first_autopat[1] --> Autopat.next --> NULL 6531 * Autopat.cmds 6532 * | 6533 * V 6534 * AutoCmd.next 6535 * | 6536 * V 6537 * NULL 6538 * etc. 6539 * 6540 * The order of AutoCmds is important, this is the order in which they were 6541 * defined and will have to be executed. 6542 */ 6543 typedef struct AutoCmd 6544 { 6545 char_u *cmd; /* The command to be executed (NULL 6546 when command has been removed) */ 6547 char nested; /* If autocommands nest here */ 6548 char last; /* last command in list */ 6549 #ifdef FEAT_EVAL 6550 scid_T scriptID; /* script ID where defined */ 6551 #endif 6552 struct AutoCmd *next; /* Next AutoCmd in list */ 6553 } AutoCmd; 6554 6555 typedef struct AutoPat 6556 { 6557 int group; /* group ID */ 6558 char_u *pat; /* pattern as typed (NULL when pattern 6559 has been removed) */ 6560 int patlen; /* strlen() of pat */ 6561 char_u *reg_pat; /* pattern converted to regexp */ 6562 char allow_dirs; /* Pattern may match whole path */ 6563 char last; /* last pattern for apply_autocmds() */ 6564 AutoCmd *cmds; /* list of commands to do */ 6565 struct AutoPat *next; /* next AutoPat in AutoPat list */ 6566 } AutoPat; 6567 6568 static struct event_name 6569 { 6570 char *name; /* event name */ 6571 EVENT_T event; /* event number */ 6572 } event_names[] = 6573 { 6574 {"BufAdd", EVENT_BUFADD}, 6575 {"BufCreate", EVENT_BUFADD}, 6576 {"BufDelete", EVENT_BUFDELETE}, 6577 {"BufEnter", EVENT_BUFENTER}, 6578 {"BufFilePost", EVENT_BUFFILEPOST}, 6579 {"BufFilePre", EVENT_BUFFILEPRE}, 6580 {"BufHidden", EVENT_BUFHIDDEN}, 6581 {"BufLeave", EVENT_BUFLEAVE}, 6582 {"BufNew", EVENT_BUFNEW}, 6583 {"BufNewFile", EVENT_BUFNEWFILE}, 6584 {"BufRead", EVENT_BUFREADPOST}, 6585 {"BufReadCmd", EVENT_BUFREADCMD}, 6586 {"BufReadPost", EVENT_BUFREADPOST}, 6587 {"BufReadPre", EVENT_BUFREADPRE}, 6588 {"BufUnload", EVENT_BUFUNLOAD}, 6589 {"BufWinEnter", EVENT_BUFWINENTER}, 6590 {"BufWinLeave", EVENT_BUFWINLEAVE}, 6591 {"BufWipeout", EVENT_BUFWIPEOUT}, 6592 {"BufWrite", EVENT_BUFWRITEPRE}, 6593 {"BufWritePost", EVENT_BUFWRITEPOST}, 6594 {"BufWritePre", EVENT_BUFWRITEPRE}, 6595 {"BufWriteCmd", EVENT_BUFWRITECMD}, 6596 {"CmdwinEnter", EVENT_CMDWINENTER}, 6597 {"CmdwinLeave", EVENT_CMDWINLEAVE}, 6598 {"ColorScheme", EVENT_COLORSCHEME}, 6599 {"EncodingChanged", EVENT_ENCODINGCHANGED}, 6600 {"FileEncoding", EVENT_ENCODINGCHANGED}, 6601 {"CursorHold", EVENT_CURSORHOLD}, 6602 {"FileAppendPost", EVENT_FILEAPPENDPOST}, 6603 {"FileAppendPre", EVENT_FILEAPPENDPRE}, 6604 {"FileAppendCmd", EVENT_FILEAPPENDCMD}, 6605 {"FileChangedShell",EVENT_FILECHANGEDSHELL}, 6606 {"FileChangedRO", EVENT_FILECHANGEDRO}, 6607 {"FileReadPost", EVENT_FILEREADPOST}, 6608 {"FileReadPre", EVENT_FILEREADPRE}, 6609 {"FileReadCmd", EVENT_FILEREADCMD}, 6610 {"FileType", EVENT_FILETYPE}, 6611 {"FileWritePost", EVENT_FILEWRITEPOST}, 6612 {"FileWritePre", EVENT_FILEWRITEPRE}, 6613 {"FileWriteCmd", EVENT_FILEWRITECMD}, 6614 {"FilterReadPost", EVENT_FILTERREADPOST}, 6615 {"FilterReadPre", EVENT_FILTERREADPRE}, 6616 {"FilterWritePost", EVENT_FILTERWRITEPOST}, 6617 {"FilterWritePre", EVENT_FILTERWRITEPRE}, 6618 {"FocusGained", EVENT_FOCUSGAINED}, 6619 {"FocusLost", EVENT_FOCUSLOST}, 6620 {"FuncUndefined", EVENT_FUNCUNDEFINED}, 6621 {"GUIEnter", EVENT_GUIENTER}, 6622 {"InsertChange", EVENT_INSERTCHANGE}, 6623 {"InsertEnter", EVENT_INSERTENTER}, 6624 {"InsertLeave", EVENT_INSERTLEAVE}, 6625 {"RemoteReply", EVENT_REMOTEREPLY}, 6626 {"StdinReadPost", EVENT_STDINREADPOST}, 6627 {"StdinReadPre", EVENT_STDINREADPRE}, 6628 {"Syntax", EVENT_SYNTAX}, 6629 {"TermChanged", EVENT_TERMCHANGED}, 6630 {"TermResponse", EVENT_TERMRESPONSE}, 6631 {"User", EVENT_USER}, 6632 {"VimEnter", EVENT_VIMENTER}, 6633 {"VimLeave", EVENT_VIMLEAVE}, 6634 {"VimLeavePre", EVENT_VIMLEAVEPRE}, 6635 {"WinEnter", EVENT_WINENTER}, 6636 {"WinLeave", EVENT_WINLEAVE}, 6637 {NULL, (EVENT_T)0} 6638 }; 6639 6640 static AutoPat *first_autopat[NUM_EVENTS] = 6641 { 6642 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, 6643 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, 6644 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, 6645 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, 6646 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, 6647 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL 6648 }; 6649 6650 /* 6651 * struct used to keep status while executing autocommands for an event. 6652 */ 6653 typedef struct AutoPatCmd 6654 { 6655 AutoPat *curpat; /* next AutoPat to examine */ 6656 AutoCmd *nextcmd; /* next AutoCmd to execute */ 6657 int group; /* group being used */ 6658 char_u *fname; /* fname to match with */ 6659 char_u *sfname; /* sfname to match with */ 6660 char_u *tail; /* tail of fname */ 6661 EVENT_T event; /* current event */ 6662 } AutoPatCmd; 6663 6664 /* 6665 * augroups stores a list of autocmd group names. 6666 */ 6667 garray_T augroups = {0, 0, sizeof(char_u *), 10, NULL}; 6668 #define AUGROUP_NAME(i) (((char_u **)augroups.ga_data)[i]) 6669 6670 /* 6671 * The ID of the current group. Group 0 is the default one. 6672 */ 6673 #define AUGROUP_DEFAULT -1 /* default autocmd group */ 6674 #define AUGROUP_ERROR -2 /* errornouse autocmd group */ 6675 #define AUGROUP_ALL -3 /* all autocmd groups */ 6676 static int current_augroup = AUGROUP_DEFAULT; 6677 6678 static int au_need_clean = FALSE; /* need to delete marked patterns */ 6679 6680 static void show_autocmd __ARGS((AutoPat *ap, EVENT_T event)); 6681 static void au_remove_pat __ARGS((AutoPat *ap)); 6682 static void au_remove_cmds __ARGS((AutoPat *ap)); 6683 static void au_cleanup __ARGS((void)); 6684 static int au_new_group __ARGS((char_u *name)); 6685 static void au_del_group __ARGS((char_u *name)); 6686 static int au_find_group __ARGS((char_u *name)); 6687 static EVENT_T event_name2nr __ARGS((char_u *start, char_u **end)); 6688 static char_u *event_nr2name __ARGS((EVENT_T event)); 6689 static char_u *find_end_event __ARGS((char_u *arg, int have_group)); 6690 static int event_ignored __ARGS((EVENT_T event)); 6691 static int au_get_grouparg __ARGS((char_u **argp)); 6692 static int do_autocmd_event __ARGS((EVENT_T event, char_u *pat, int nested, char_u *cmd, int forceit, int group)); 6693 static char_u *getnextac __ARGS((int c, void *cookie, int indent)); 6694 static int apply_autocmds_group __ARGS((EVENT_T event, char_u *fname, char_u *fname_io, int force, int group, buf_T *buf, exarg_T *eap)); 6695 static void auto_next_pat __ARGS((AutoPatCmd *apc, int stop_at_last)); 6696 6697 static EVENT_T last_event; 6698 static int last_group; 6699 6700 /* 6701 * Show the autocommands for one AutoPat. 6702 */ 6703 static void 6704 show_autocmd(ap, event) 6705 AutoPat *ap; 6706 EVENT_T event; 6707 { 6708 AutoCmd *ac; 6709 6710 /* Check for "got_int" (here and at various places below), which is set 6711 * when "q" has been hit for the "--more--" prompt */ 6712 if (got_int) 6713 return; 6714 if (ap->pat == NULL) /* pattern has been removed */ 6715 return; 6716 6717 msg_putchar('\n'); 6718 if (got_int) 6719 return; 6720 if (event != last_event || ap->group != last_group) 6721 { 6722 if (ap->group != AUGROUP_DEFAULT) 6723 { 6724 if (AUGROUP_NAME(ap->group) == NULL) 6725 msg_puts_attr((char_u *)_("--Deleted--"), hl_attr(HLF_E)); 6726 else 6727 msg_puts_attr(AUGROUP_NAME(ap->group), hl_attr(HLF_T)); 6728 msg_puts((char_u *)" "); 6729 } 6730 msg_puts_attr(event_nr2name(event), hl_attr(HLF_T)); 6731 last_event = event; 6732 last_group = ap->group; 6733 msg_putchar('\n'); 6734 if (got_int) 6735 return; 6736 } 6737 msg_col = 4; 6738 msg_outtrans(ap->pat); 6739 6740 for (ac = ap->cmds; ac != NULL; ac = ac->next) 6741 { 6742 if (ac->cmd != NULL) /* skip removed commands */ 6743 { 6744 if (msg_col >= 14) 6745 msg_putchar('\n'); 6746 msg_col = 14; 6747 if (got_int) 6748 return; 6749 msg_outtrans(ac->cmd); 6750 if (got_int) 6751 return; 6752 if (ac->next != NULL) 6753 { 6754 msg_putchar('\n'); 6755 if (got_int) 6756 return; 6757 } 6758 } 6759 } 6760 } 6761 6762 /* 6763 * Mark an autocommand pattern for deletion. 6764 */ 6765 static void 6766 au_remove_pat(ap) 6767 AutoPat *ap; 6768 { 6769 vim_free(ap->pat); 6770 ap->pat = NULL; 6771 au_need_clean = TRUE; 6772 } 6773 6774 /* 6775 * Mark all commands for a pattern for deletion. 6776 */ 6777 static void 6778 au_remove_cmds(ap) 6779 AutoPat *ap; 6780 { 6781 AutoCmd *ac; 6782 6783 for (ac = ap->cmds; ac != NULL; ac = ac->next) 6784 { 6785 vim_free(ac->cmd); 6786 ac->cmd = NULL; 6787 } 6788 au_need_clean = TRUE; 6789 } 6790 6791 /* 6792 * Cleanup autocommands and patterns that have been deleted. 6793 * This is only done when not executing autocommands. 6794 */ 6795 static void 6796 au_cleanup() 6797 { 6798 AutoPat *ap, **prev_ap; 6799 AutoCmd *ac, **prev_ac; 6800 EVENT_T event; 6801 6802 if (autocmd_busy || !au_need_clean) 6803 return; 6804 6805 /* loop over all events */ 6806 for (event = (EVENT_T)0; (int)event < (int)NUM_EVENTS; 6807 event = (EVENT_T)((int)event + 1)) 6808 { 6809 /* loop over all autocommand patterns */ 6810 prev_ap = &(first_autopat[(int)event]); 6811 for (ap = *prev_ap; ap != NULL; ap = *prev_ap) 6812 { 6813 /* loop over all commands for this pattern */ 6814 prev_ac = &(ap->cmds); 6815 for (ac = *prev_ac; ac != NULL; ac = *prev_ac) 6816 { 6817 /* remove the command if the pattern is to be deleted or when 6818 * the command has been marked for deletion */ 6819 if (ap->pat == NULL || ac->cmd == NULL) 6820 { 6821 *prev_ac = ac->next; 6822 vim_free(ac->cmd); 6823 vim_free(ac); 6824 } 6825 else 6826 prev_ac = &(ac->next); 6827 } 6828 6829 /* remove the pattern if it has been marked for deletion */ 6830 if (ap->pat == NULL) 6831 { 6832 *prev_ap = ap->next; 6833 vim_free(ap->reg_pat); 6834 vim_free(ap); 6835 } 6836 else 6837 prev_ap = &(ap->next); 6838 } 6839 } 6840 6841 au_need_clean = FALSE; 6842 } 6843 6844 /* 6845 * Add an autocmd group name. 6846 * Return it's ID. Returns AUGROUP_ERROR (< 0) for error. 6847 */ 6848 static int 6849 au_new_group(name) 6850 char_u *name; 6851 { 6852 int i; 6853 6854 i = au_find_group(name); 6855 if (i == AUGROUP_ERROR) /* the group doesn't exist yet, add it */ 6856 { 6857 /* First try using a free entry. */ 6858 for (i = 0; i < augroups.ga_len; ++i) 6859 if (AUGROUP_NAME(i) == NULL) 6860 break; 6861 if (i == augroups.ga_len && ga_grow(&augroups, 1) == FAIL) 6862 return AUGROUP_ERROR; 6863 6864 AUGROUP_NAME(i) = vim_strsave(name); 6865 if (AUGROUP_NAME(i) == NULL) 6866 return AUGROUP_ERROR; 6867 if (i == augroups.ga_len) 6868 { 6869 ++augroups.ga_len; 6870 --augroups.ga_room; 6871 } 6872 } 6873 6874 return i; 6875 } 6876 6877 static void 6878 au_del_group(name) 6879 char_u *name; 6880 { 6881 int i; 6882 6883 i = au_find_group(name); 6884 if (i == AUGROUP_ERROR) /* the group doesn't exist */ 6885 EMSG2(_("E367: No such group: \"%s\""), name); 6886 else 6887 { 6888 vim_free(AUGROUP_NAME(i)); 6889 AUGROUP_NAME(i) = NULL; 6890 } 6891 } 6892 6893 /* 6894 * Find the ID of an autocmd group name. 6895 * Return it's ID. Returns AUGROUP_ERROR (< 0) for error. 6896 */ 6897 static int 6898 au_find_group(name) 6899 char_u *name; 6900 { 6901 int i; 6902 6903 for (i = 0; i < augroups.ga_len; ++i) 6904 if (AUGROUP_NAME(i) != NULL && STRCMP(AUGROUP_NAME(i), name) == 0) 6905 return i; 6906 return AUGROUP_ERROR; 6907 } 6908 6909 /* 6910 * ":augroup {name}". 6911 */ 6912 void 6913 do_augroup(arg, del_group) 6914 char_u *arg; 6915 int del_group; 6916 { 6917 int i; 6918 6919 if (del_group) 6920 { 6921 if (*arg == NUL) 6922 EMSG(_(e_argreq)); 6923 else 6924 au_del_group(arg); 6925 } 6926 else if (STRICMP(arg, "end") == 0) /* ":aug end": back to group 0 */ 6927 current_augroup = AUGROUP_DEFAULT; 6928 else if (*arg) /* ":aug xxx": switch to group xxx */ 6929 { 6930 i = au_new_group(arg); 6931 if (i != AUGROUP_ERROR) 6932 current_augroup = i; 6933 } 6934 else /* ":aug": list the group names */ 6935 { 6936 msg_start(); 6937 for (i = 0; i < augroups.ga_len; ++i) 6938 { 6939 if (AUGROUP_NAME(i) != NULL) 6940 { 6941 msg_puts(AUGROUP_NAME(i)); 6942 msg_puts((char_u *)" "); 6943 } 6944 } 6945 msg_clr_eos(); 6946 msg_end(); 6947 } 6948 } 6949 6950 /* 6951 * Return the event number for event name "start". 6952 * Return NUM_EVENTS if the event name was not found. 6953 * Return a pointer to the next event name in "end". 6954 */ 6955 static EVENT_T 6956 event_name2nr(start, end) 6957 char_u *start; 6958 char_u **end; 6959 { 6960 char_u *p; 6961 int i; 6962 int len; 6963 6964 /* the event name ends with end of line, a blank or a comma */ 6965 for (p = start; *p && !vim_iswhite(*p) && *p != ','; ++p) 6966 ; 6967 for (i = 0; event_names[i].name != NULL; ++i) 6968 { 6969 len = (int)STRLEN(event_names[i].name); 6970 if (len == p - start && STRNICMP(event_names[i].name, start, len) == 0) 6971 break; 6972 } 6973 if (*p == ',') 6974 ++p; 6975 *end = p; 6976 if (event_names[i].name == NULL) 6977 return NUM_EVENTS; 6978 return event_names[i].event; 6979 } 6980 6981 /* 6982 * Return the name for event "event". 6983 */ 6984 static char_u * 6985 event_nr2name(event) 6986 EVENT_T event; 6987 { 6988 int i; 6989 6990 for (i = 0; event_names[i].name != NULL; ++i) 6991 if (event_names[i].event == event) 6992 return (char_u *)event_names[i].name; 6993 return (char_u *)"Unknown"; 6994 } 6995 6996 /* 6997 * Scan over the events. "*" stands for all events. 6998 */ 6999 static char_u * 7000 find_end_event(arg, have_group) 7001 char_u *arg; 7002 int have_group; /* TRUE when group name was found */ 7003 { 7004 char_u *pat; 7005 char_u *p; 7006 7007 if (*arg == '*') 7008 { 7009 if (arg[1] && !vim_iswhite(arg[1])) 7010 { 7011 EMSG2(_("E215: Illegal character after *: %s"), arg); 7012 return NULL; 7013 } 7014 pat = arg + 1; 7015 } 7016 else 7017 { 7018 for (pat = arg; *pat && !vim_iswhite(*pat); pat = p) 7019 { 7020 if ((int)event_name2nr(pat, &p) >= (int)NUM_EVENTS) 7021 { 7022 if (have_group) 7023 EMSG2(_("E216: No such event: %s"), pat); 7024 else 7025 EMSG2(_("E216: No such group or event: %s"), pat); 7026 return NULL; 7027 } 7028 } 7029 } 7030 return pat; 7031 } 7032 7033 /* 7034 * Return TRUE if "event" is included in 'eventignore'. 7035 */ 7036 static int 7037 event_ignored(event) 7038 EVENT_T event; 7039 { 7040 char_u *p = p_ei; 7041 7042 if (STRICMP(p_ei, "all") == 0) 7043 return TRUE; 7044 7045 while (*p) 7046 if (event_name2nr(p, &p) == event) 7047 return TRUE; 7048 7049 return FALSE; 7050 } 7051 7052 /* 7053 * Return OK when the contents of p_ei is valid, FAIL otherwise. 7054 */ 7055 int 7056 check_ei() 7057 { 7058 char_u *p = p_ei; 7059 7060 if (STRICMP(p_ei, "all") == 0) 7061 return OK; 7062 7063 while (*p) 7064 if (event_name2nr(p, &p) == NUM_EVENTS) 7065 return FAIL; 7066 7067 return OK; 7068 } 7069 7070 /* 7071 * do_autocmd() -- implements the :autocmd command. Can be used in the 7072 * following ways: 7073 * 7074 * :autocmd <event> <pat> <cmd> Add <cmd> to the list of commands that 7075 * will be automatically executed for <event> 7076 * when editing a file matching <pat>, in 7077 * the current group. 7078 * :autocmd <event> <pat> Show the auto-commands associated with 7079 * <event> and <pat>. 7080 * :autocmd <event> Show the auto-commands associated with 7081 * <event>. 7082 * :autocmd Show all auto-commands. 7083 * :autocmd! <event> <pat> <cmd> Remove all auto-commands associated with 7084 * <event> and <pat>, and add the command 7085 * <cmd>, for the current group. 7086 * :autocmd! <event> <pat> Remove all auto-commands associated with 7087 * <event> and <pat> for the current group. 7088 * :autocmd! <event> Remove all auto-commands associated with 7089 * <event> for the current group. 7090 * :autocmd! Remove ALL auto-commands for the current 7091 * group. 7092 * 7093 * Multiple events and patterns may be given separated by commas. Here are 7094 * some examples: 7095 * :autocmd bufread,bufenter *.c,*.h set tw=0 smartindent noic 7096 * :autocmd bufleave * set tw=79 nosmartindent ic infercase 7097 * 7098 * :autocmd * *.c show all autocommands for *.c files. 7099 */ 7100 void 7101 do_autocmd(arg, forceit) 7102 char_u *arg; 7103 int forceit; 7104 { 7105 char_u *pat; 7106 char_u *envpat = NULL; 7107 char_u *cmd; 7108 EVENT_T event; 7109 int need_free = FALSE; 7110 int nested = FALSE; 7111 int group; 7112 7113 /* 7114 * Check for a legal group name. If not, use AUGROUP_ALL. 7115 */ 7116 group = au_get_grouparg(&arg); 7117 if (arg == NULL) /* out of memory */ 7118 return; 7119 7120 /* 7121 * Scan over the events. 7122 * If we find an illegal name, return here, don't do anything. 7123 */ 7124 pat = find_end_event(arg, group != AUGROUP_ALL); 7125 if (pat == NULL) 7126 return; 7127 7128 /* 7129 * Scan over the pattern. Put a NUL at the end. 7130 */ 7131 pat = skipwhite(pat); 7132 cmd = pat; 7133 while (*cmd && (!vim_iswhite(*cmd) || cmd[-1] == '\\')) 7134 cmd++; 7135 if (*cmd) 7136 *cmd++ = NUL; 7137 7138 /* Expand environment variables in the pattern. Set 'shellslash', we want 7139 * forward slashes here. */ 7140 if (vim_strchr(pat, '$') != NULL || vim_strchr(pat, '~') != NULL) 7141 { 7142 #ifdef BACKSLASH_IN_FILENAME 7143 int p_ssl_save = p_ssl; 7144 7145 p_ssl = TRUE; 7146 #endif 7147 envpat = expand_env_save(pat); 7148 #ifdef BACKSLASH_IN_FILENAME 7149 p_ssl = p_ssl_save; 7150 #endif 7151 if (envpat != NULL) 7152 pat = envpat; 7153 } 7154 7155 /* 7156 * Check for "nested" flag. 7157 */ 7158 cmd = skipwhite(cmd); 7159 if (*cmd != NUL && STRNCMP(cmd, "nested", 6) == 0 && vim_iswhite(cmd[6])) 7160 { 7161 nested = TRUE; 7162 cmd = skipwhite(cmd + 6); 7163 } 7164 7165 /* 7166 * Find the start of the commands. 7167 * Expand <sfile> in it. 7168 */ 7169 if (*cmd != NUL) 7170 { 7171 cmd = expand_sfile(cmd); 7172 if (cmd == NULL) /* some error */ 7173 return; 7174 need_free = TRUE; 7175 } 7176 7177 /* 7178 * Print header when showing autocommands. 7179 */ 7180 if (!forceit && *cmd == NUL) 7181 { 7182 /* Highlight title */ 7183 MSG_PUTS_TITLE(_("\n--- Auto-Commands ---")); 7184 } 7185 7186 /* 7187 * Loop over the events. 7188 */ 7189 last_event = (EVENT_T)-1; /* for listing the event name */ 7190 last_group = AUGROUP_ERROR; /* for listing the group name */ 7191 if (*arg == '*' || *arg == NUL) 7192 { 7193 for (event = (EVENT_T)0; (int)event < (int)NUM_EVENTS; 7194 event = (EVENT_T)((int)event + 1)) 7195 if (do_autocmd_event(event, pat, 7196 nested, cmd, forceit, group) == FAIL) 7197 break; 7198 } 7199 else 7200 { 7201 while (*arg && !vim_iswhite(*arg)) 7202 if (do_autocmd_event(event_name2nr(arg, &arg), pat, 7203 nested, cmd, forceit, group) == FAIL) 7204 break; 7205 } 7206 7207 if (need_free) 7208 vim_free(cmd); 7209 vim_free(envpat); 7210 } 7211 7212 /* 7213 * Find the group ID in a ":autocmd" or ":doautocmd" argument. 7214 * The "argp" argument is advanced to the following argument. 7215 * 7216 * Returns the group ID, AUGROUP_ERROR for error (out of memory). 7217 */ 7218 static int 7219 au_get_grouparg(argp) 7220 char_u **argp; 7221 { 7222 char_u *group_name; 7223 char_u *p; 7224 char_u *arg = *argp; 7225 int group = AUGROUP_ALL; 7226 7227 p = skiptowhite(arg); 7228 if (p > arg) 7229 { 7230 group_name = vim_strnsave(arg, (int)(p - arg)); 7231 if (group_name == NULL) /* out of memory */ 7232 return AUGROUP_ERROR; 7233 group = au_find_group(group_name); 7234 if (group == AUGROUP_ERROR) 7235 group = AUGROUP_ALL; /* no match, use all groups */ 7236 else 7237 *argp = skipwhite(p); /* match, skip over group name */ 7238 vim_free(group_name); 7239 } 7240 return group; 7241 } 7242 7243 /* 7244 * do_autocmd() for one event. 7245 * If *pat == NUL do for all patterns. 7246 * If *cmd == NUL show entries. 7247 * If forceit == TRUE delete entries. 7248 * If group is not AUGROUP_ALL, only use this group. 7249 */ 7250 static int 7251 do_autocmd_event(event, pat, nested, cmd, forceit, group) 7252 EVENT_T event; 7253 char_u *pat; 7254 int nested; 7255 char_u *cmd; 7256 int forceit; 7257 int group; 7258 { 7259 AutoPat *ap; 7260 AutoPat **prev_ap; 7261 AutoCmd *ac; 7262 AutoCmd **prev_ac; 7263 int brace_level; 7264 char_u *endpat; 7265 int findgroup; 7266 int allgroups; 7267 int patlen; 7268 7269 if (group == AUGROUP_ALL) 7270 findgroup = current_augroup; 7271 else 7272 findgroup = group; 7273 allgroups = (group == AUGROUP_ALL && !forceit && *cmd == NUL); 7274 7275 /* 7276 * Show or delete all patterns for an event. 7277 */ 7278 if (*pat == NUL) 7279 { 7280 for (ap = first_autopat[(int)event]; ap != NULL; ap = ap->next) 7281 { 7282 if (forceit) /* delete the AutoPat, if it's in the current group */ 7283 { 7284 if (ap->group == findgroup) 7285 au_remove_pat(ap); 7286 } 7287 else if (group == AUGROUP_ALL || ap->group == group) 7288 show_autocmd(ap, event); 7289 } 7290 } 7291 7292 /* 7293 * Loop through all the specified patterns. 7294 */ 7295 for ( ; *pat; pat = (*endpat == ',' ? endpat + 1 : endpat)) 7296 { 7297 /* 7298 * Find end of the pattern. 7299 * Watch out for a comma in braces, like "*.\{obj,o\}". 7300 */ 7301 brace_level = 0; 7302 for (endpat = pat; *endpat && (*endpat != ',' || brace_level 7303 || endpat[-1] == '\\'); ++endpat) 7304 { 7305 if (*endpat == '{') 7306 brace_level++; 7307 else if (*endpat == '}') 7308 brace_level--; 7309 } 7310 if (pat == endpat) /* ignore single comma */ 7311 continue; 7312 patlen = (int)(endpat - pat); 7313 7314 /* 7315 * Find AutoPat entries with this pattern. 7316 */ 7317 prev_ap = &first_autopat[(int)event]; 7318 while ((ap = *prev_ap) != NULL) 7319 { 7320 if (ap->pat != NULL) 7321 { 7322 /* Accept a pattern when: 7323 * - a group was specified and it's that group, or a group was 7324 * not specified and it's the current group, or a group was 7325 * not specified and we are listing 7326 * - the length of the pattern matches 7327 * - the pattern matches 7328 */ 7329 if ((allgroups || ap->group == findgroup) 7330 && ap->patlen == patlen 7331 && STRNCMP(pat, ap->pat, patlen) == 0) 7332 { 7333 /* 7334 * Remove existing autocommands. 7335 * If adding any new autocmd's for this AutoPat, don't 7336 * delete the pattern from the autopat list, append to 7337 * this list. 7338 */ 7339 if (forceit) 7340 { 7341 if (*cmd != NUL && ap->next == NULL) 7342 { 7343 au_remove_cmds(ap); 7344 break; 7345 } 7346 au_remove_pat(ap); 7347 } 7348 7349 /* 7350 * Show autocmd's for this autopat 7351 */ 7352 else if (*cmd == NUL) 7353 show_autocmd(ap, event); 7354 7355 /* 7356 * Add autocmd to this autopat, if it's the last one. 7357 */ 7358 else if (ap->next == NULL) 7359 break; 7360 } 7361 } 7362 prev_ap = &ap->next; 7363 } 7364 7365 /* 7366 * Add a new command. 7367 */ 7368 if (*cmd != NUL) 7369 { 7370 /* 7371 * If the pattern we want to add a command to does appear at the 7372 * end of the list (or not is not in the list at all), add the 7373 * pattern at the end of the list. 7374 */ 7375 if (ap == NULL) 7376 { 7377 ap = (AutoPat *)alloc((unsigned)sizeof(AutoPat)); 7378 if (ap == NULL) 7379 return FAIL; 7380 ap->pat = vim_strnsave(pat, patlen); 7381 ap->patlen = patlen; 7382 if (ap->pat == NULL) 7383 { 7384 vim_free(ap); 7385 return FAIL; 7386 } 7387 ap->reg_pat = file_pat_to_reg_pat(pat, endpat, 7388 &ap->allow_dirs, TRUE); 7389 if (ap->reg_pat == NULL) 7390 { 7391 vim_free(ap->pat); 7392 vim_free(ap); 7393 return FAIL; 7394 } 7395 ap->cmds = NULL; 7396 *prev_ap = ap; 7397 ap->next = NULL; 7398 if (group == AUGROUP_ALL) 7399 ap->group = current_augroup; 7400 else 7401 ap->group = group; 7402 } 7403 7404 /* 7405 * Add the autocmd at the end of the AutoCmd list. 7406 */ 7407 prev_ac = &(ap->cmds); 7408 while ((ac = *prev_ac) != NULL) 7409 prev_ac = &ac->next; 7410 ac = (AutoCmd *)alloc((unsigned)sizeof(AutoCmd)); 7411 if (ac == NULL) 7412 return FAIL; 7413 ac->cmd = vim_strsave(cmd); 7414 #ifdef FEAT_EVAL 7415 ac->scriptID = current_SID; 7416 #endif 7417 if (ac->cmd == NULL) 7418 { 7419 vim_free(ac); 7420 return FAIL; 7421 } 7422 ac->next = NULL; 7423 *prev_ac = ac; 7424 ac->nested = nested; 7425 } 7426 } 7427 7428 au_cleanup(); /* may really delete removed patterns/commands now */ 7429 return OK; 7430 } 7431 7432 /* 7433 * Implementation of ":doautocmd [group] event [fname]". 7434 * Return OK for success, FAIL for failure; 7435 */ 7436 int 7437 do_doautocmd(arg, do_msg) 7438 char_u *arg; 7439 int do_msg; /* give message for no matching autocmds? */ 7440 { 7441 char_u *fname; 7442 int nothing_done = TRUE; 7443 int group; 7444 7445 /* 7446 * Check for a legal group name. If not, use AUGROUP_ALL. 7447 */ 7448 group = au_get_grouparg(&arg); 7449 if (arg == NULL) /* out of memory */ 7450 return FAIL; 7451 7452 if (*arg == '*') 7453 { 7454 EMSG(_("E217: Can't execute autocommands for ALL events")); 7455 return FAIL; 7456 } 7457 7458 /* 7459 * Scan over the events. 7460 * If we find an illegal name, return here, don't do anything. 7461 */ 7462 fname = find_end_event(arg, group != AUGROUP_ALL); 7463 if (fname == NULL) 7464 return FAIL; 7465 7466 fname = skipwhite(fname); 7467 7468 /* 7469 * Loop over the events. 7470 */ 7471 while (*arg && !vim_iswhite(*arg)) 7472 if (apply_autocmds_group(event_name2nr(arg, &arg), 7473 fname, NULL, TRUE, group, curbuf, NULL)) 7474 nothing_done = FALSE; 7475 7476 if (nothing_done && do_msg) 7477 MSG(_("No matching autocommands")); 7478 7479 #ifdef FEAT_EVAL 7480 return aborting() ? FAIL : OK; 7481 #else 7482 return OK; 7483 #endif 7484 } 7485 7486 /* 7487 * ":doautoall": execute autocommands for each loaded buffer. 7488 */ 7489 void 7490 ex_doautoall(eap) 7491 exarg_T *eap; 7492 { 7493 int retval; 7494 aco_save_T aco; 7495 buf_T *buf; 7496 7497 /* 7498 * This is a bit tricky: For some commands curwin->w_buffer needs to be 7499 * equal to curbuf, but for some buffers there may not be a window. 7500 * So we change the buffer for the current window for a moment. This 7501 * gives problems when the autocommands make changes to the list of 7502 * buffers or windows... 7503 */ 7504 for (buf = firstbuf; buf != NULL; buf = buf->b_next) 7505 { 7506 if (curbuf->b_ml.ml_mfp != NULL) 7507 { 7508 /* find a window for this buffer and save some values */ 7509 aucmd_prepbuf(&aco, buf); 7510 7511 /* execute the autocommands for this buffer */ 7512 retval = do_doautocmd(eap->arg, FALSE); 7513 do_modelines(); 7514 7515 /* restore the current window */ 7516 aucmd_restbuf(&aco); 7517 7518 /* stop if there is some error or buffer was deleted */ 7519 if (retval == FAIL || !buf_valid(buf)) 7520 break; 7521 } 7522 } 7523 7524 check_cursor(); /* just in case lines got deleted */ 7525 } 7526 7527 /* 7528 * Prepare for executing autocommands for (hidden) buffer "buf". 7529 * Search a window for the current buffer. Save the cursor position and 7530 * screen offset. 7531 * Set "curbuf" and "curwin" to match "buf". 7532 */ 7533 void 7534 aucmd_prepbuf(aco, buf) 7535 aco_save_T *aco; /* structure to save values in */ 7536 buf_T *buf; /* new curbuf */ 7537 { 7538 win_T *win; 7539 7540 aco->new_curbuf = buf; 7541 7542 /* Find a window that is for the new buffer */ 7543 if (buf == curbuf) /* be quick when buf is curbuf */ 7544 win = curwin; 7545 else 7546 #ifdef FEAT_WINDOWS 7547 for (win = firstwin; win != NULL; win = win->w_next) 7548 if (win->w_buffer == buf) 7549 break; 7550 #else 7551 win = NULL; 7552 #endif 7553 7554 /* 7555 * Prefer to use an existing window for the buffer, it has the least side 7556 * effects (esp. if "buf" is curbuf). 7557 * Otherwise, use curwin for "buf". It might make some items in the 7558 * window invalid. At least save the cursor and topline. 7559 */ 7560 if (win != NULL) 7561 { 7562 /* there is a window for "buf", make it the curwin */ 7563 aco->save_curwin = curwin; 7564 curwin = win; 7565 aco->save_buf = win->w_buffer; 7566 aco->new_curwin = win; 7567 } 7568 else 7569 { 7570 /* there is no window for "buf", use curwin */ 7571 aco->save_curwin = NULL; 7572 aco->save_buf = curbuf; 7573 --curbuf->b_nwindows; 7574 curwin->w_buffer = buf; 7575 ++buf->b_nwindows; 7576 7577 /* save cursor and topline, set them to safe values */ 7578 aco->save_cursor = curwin->w_cursor; 7579 curwin->w_cursor.lnum = 1; 7580 curwin->w_cursor.col = 0; 7581 aco->save_topline = curwin->w_topline; 7582 curwin->w_topline = 1; 7583 #ifdef FEAT_DIFF 7584 aco->save_topfill = curwin->w_topfill; 7585 curwin->w_topfill = 0; 7586 #endif 7587 } 7588 7589 curbuf = buf; 7590 } 7591 7592 /* 7593 * Cleanup after executing autocommands for a (hidden) buffer. 7594 * Restore the window as it was (if possible). 7595 */ 7596 void 7597 aucmd_restbuf(aco) 7598 aco_save_T *aco; /* structure holding saved values */ 7599 { 7600 if (aco->save_curwin != NULL) 7601 { 7602 /* restore curwin */ 7603 #ifdef FEAT_WINDOWS 7604 if (win_valid(aco->save_curwin)) 7605 #endif 7606 { 7607 /* restore the buffer which was previously edited by curwin, if 7608 * it's still the same window and it's valid */ 7609 if (curwin == aco->new_curwin 7610 && buf_valid(aco->save_buf) 7611 && aco->save_buf->b_ml.ml_mfp != NULL) 7612 { 7613 --curbuf->b_nwindows; 7614 curbuf = aco->save_buf; 7615 curwin->w_buffer = curbuf; 7616 ++curbuf->b_nwindows; 7617 } 7618 7619 curwin = aco->save_curwin; 7620 curbuf = curwin->w_buffer; 7621 } 7622 } 7623 else 7624 { 7625 /* restore buffer for curwin if it still exists and is loaded */ 7626 if (buf_valid(aco->save_buf) && aco->save_buf->b_ml.ml_mfp != NULL) 7627 { 7628 --curbuf->b_nwindows; 7629 curbuf = aco->save_buf; 7630 curwin->w_buffer = curbuf; 7631 ++curbuf->b_nwindows; 7632 curwin->w_cursor = aco->save_cursor; 7633 check_cursor(); 7634 /* check topline < line_count, in case lines got deleted */ 7635 if (aco->save_topline <= curbuf->b_ml.ml_line_count) 7636 { 7637 curwin->w_topline = aco->save_topline; 7638 #ifdef FEAT_DIFF 7639 curwin->w_topfill = aco->save_topfill; 7640 #endif 7641 } 7642 else 7643 { 7644 curwin->w_topline = curbuf->b_ml.ml_line_count; 7645 #ifdef FEAT_DIFF 7646 curwin->w_topfill = 0; 7647 #endif 7648 } 7649 } 7650 } 7651 } 7652 7653 static int autocmd_nested = FALSE; 7654 7655 /* 7656 * Execute autocommands for "event" and file name "fname". 7657 * Return TRUE if some commands were executed. 7658 */ 7659 int 7660 apply_autocmds(event, fname, fname_io, force, buf) 7661 EVENT_T event; 7662 char_u *fname; /* NULL or empty means use actual file name */ 7663 char_u *fname_io; /* fname to use for <afile> on cmdline */ 7664 int force; /* when TRUE, ignore autocmd_busy */ 7665 buf_T *buf; /* buffer for <abuf> */ 7666 { 7667 return apply_autocmds_group(event, fname, fname_io, force, 7668 AUGROUP_ALL, buf, NULL); 7669 } 7670 7671 /* 7672 * Like apply_autocmds(), but with extra "eap" argument. This takes care of 7673 * setting v:filearg. 7674 */ 7675 static int 7676 apply_autocmds_exarg(event, fname, fname_io, force, buf, eap) 7677 EVENT_T event; 7678 char_u *fname; 7679 char_u *fname_io; 7680 int force; 7681 buf_T *buf; 7682 exarg_T *eap; 7683 { 7684 return apply_autocmds_group(event, fname, fname_io, force, 7685 AUGROUP_ALL, buf, eap); 7686 } 7687 7688 /* 7689 * Like apply_autocmds(), but handles the caller's retval. If the script 7690 * processing is being aborted or if retval is FAIL when inside a try 7691 * conditional, no autocommands are executed. If otherwise the autocommands 7692 * cause the script to be aborted, retval is set to FAIL. 7693 */ 7694 int 7695 apply_autocmds_retval(event, fname, fname_io, force, buf, retval) 7696 EVENT_T event; 7697 char_u *fname; /* NULL or empty means use actual file name */ 7698 char_u *fname_io; /* fname to use for <afile> on cmdline */ 7699 int force; /* when TRUE, ignore autocmd_busy */ 7700 buf_T *buf; /* buffer for <abuf> */ 7701 int *retval; /* pointer to caller's retval */ 7702 { 7703 int did_cmd; 7704 7705 if (should_abort(*retval)) 7706 return FALSE; 7707 7708 did_cmd = apply_autocmds_group(event, fname, fname_io, force, 7709 AUGROUP_ALL, buf, NULL); 7710 if (did_cmd && aborting()) 7711 *retval = FAIL; 7712 return did_cmd; 7713 } 7714 7715 #if defined(FEAT_AUTOCMD) || defined(PROTO) 7716 int 7717 has_cursorhold() 7718 { 7719 return (first_autopat[(int)EVENT_CURSORHOLD] != NULL); 7720 } 7721 #endif 7722 7723 static int 7724 apply_autocmds_group(event, fname, fname_io, force, group, buf, eap) 7725 EVENT_T event; 7726 char_u *fname; /* NULL or empty means use actual file name */ 7727 char_u *fname_io; /* fname to use for <afile> on cmdline, NULL means 7728 use fname */ 7729 int force; /* when TRUE, ignore autocmd_busy */ 7730 int group; /* group ID, or AUGROUP_ALL */ 7731 buf_T *buf; /* buffer for <abuf> */ 7732 exarg_T *eap; /* command arguments */ 7733 { 7734 char_u *sfname = NULL; /* short file name */ 7735 char_u *tail; 7736 int save_changed; 7737 buf_T *old_curbuf; 7738 int retval = FALSE; 7739 char_u *save_sourcing_name; 7740 linenr_T save_sourcing_lnum; 7741 char_u *save_autocmd_fname; 7742 int save_autocmd_bufnr; 7743 char_u *save_autocmd_match; 7744 int save_autocmd_busy; 7745 int save_autocmd_nested; 7746 static int nesting = 0; 7747 AutoPatCmd patcmd; 7748 AutoPat *ap; 7749 #ifdef FEAT_EVAL 7750 scid_T save_current_SID; 7751 void *save_funccalp; 7752 char_u *save_cmdarg; 7753 long save_cmdbang; 7754 #endif 7755 static int filechangeshell_busy = FALSE; 7756 7757 /* 7758 * Quickly return if there are no autocommands for this event or 7759 * autocommands are blocked. 7760 */ 7761 if (first_autopat[(int)event] == NULL || autocmd_block > 0) 7762 return retval; 7763 7764 /* 7765 * When autocommands are busy, new autocommands are only executed when 7766 * explicitly enabled with the "nested" flag. 7767 */ 7768 if (autocmd_busy && !(force || autocmd_nested)) 7769 return retval; 7770 7771 #ifdef FEAT_EVAL 7772 /* 7773 * Quickly return when immdediately aborting on error, or when an interrupt 7774 * occurred or an exception was thrown but not caught. 7775 */ 7776 if (aborting()) 7777 return retval; 7778 #endif 7779 7780 /* 7781 * FileChangedShell never nests, because it can create an endless loop. 7782 */ 7783 if (filechangeshell_busy && event == EVENT_FILECHANGEDSHELL) 7784 return retval; 7785 7786 /* 7787 * Ignore events in 'eventignore'. 7788 */ 7789 if (event_ignored(event)) 7790 return retval; 7791 7792 /* 7793 * Allow nesting of autocommands, but restrict the depth, because it's 7794 * possible to create an endless loop. 7795 */ 7796 if (nesting == 10) 7797 { 7798 EMSG(_("E218: autocommand nesting too deep")); 7799 return retval; 7800 } 7801 7802 /* 7803 * Check if these autocommands are disabled. Used when doing ":all" or 7804 * ":ball". 7805 */ 7806 if ( (autocmd_no_enter 7807 && (event == EVENT_WINENTER || event == EVENT_BUFENTER)) 7808 || (autocmd_no_leave 7809 && (event == EVENT_WINLEAVE || event == EVENT_BUFLEAVE))) 7810 return retval; 7811 7812 /* 7813 * Save the autocmd_* variables and info about the current buffer. 7814 */ 7815 save_autocmd_fname = autocmd_fname; 7816 save_autocmd_bufnr = autocmd_bufnr; 7817 save_autocmd_match = autocmd_match; 7818 save_autocmd_busy = autocmd_busy; 7819 save_autocmd_nested = autocmd_nested; 7820 save_changed = curbuf->b_changed; 7821 old_curbuf = curbuf; 7822 7823 /* 7824 * Set the file name to be used for <afile>. 7825 */ 7826 if (fname_io == NULL) 7827 { 7828 if (fname != NULL && *fname != NUL) 7829 autocmd_fname = fname; 7830 else if (buf != NULL) 7831 autocmd_fname = buf->b_fname; 7832 else 7833 autocmd_fname = NULL; 7834 } 7835 else 7836 autocmd_fname = fname_io; 7837 7838 /* 7839 * Set the buffer number to be used for <abuf>. 7840 */ 7841 if (buf == NULL) 7842 autocmd_bufnr = 0; 7843 else 7844 autocmd_bufnr = buf->b_fnum; 7845 7846 /* 7847 * When the file name is NULL or empty, use the file name of buffer "buf". 7848 * Always use the full path of the file name to match with, in case 7849 * "allow_dirs" is set. 7850 */ 7851 if (fname == NULL || *fname == NUL) 7852 { 7853 if (buf == NULL) 7854 fname = NULL; 7855 else 7856 { 7857 #ifdef FEAT_SYN_HL 7858 if (event == EVENT_SYNTAX) 7859 fname = buf->b_p_syn; 7860 else 7861 #endif 7862 if (event == EVENT_FILETYPE) 7863 fname = buf->b_p_ft; 7864 else 7865 { 7866 if (buf->b_sfname != NULL) 7867 sfname = vim_strsave(buf->b_sfname); 7868 fname = buf->b_ffname; 7869 } 7870 } 7871 if (fname == NULL) 7872 fname = (char_u *)""; 7873 fname = vim_strsave(fname); /* make a copy, so we can change it */ 7874 } 7875 else 7876 { 7877 sfname = vim_strsave(fname); 7878 /* Don't try expanding FileType, Syntax or WindowID. */ 7879 if (event == EVENT_FILETYPE || event == EVENT_SYNTAX 7880 || event == EVENT_REMOTEREPLY) 7881 fname = vim_strsave(fname); 7882 else 7883 fname = FullName_save(fname, FALSE); 7884 } 7885 if (fname == NULL) /* out of memory */ 7886 { 7887 vim_free(sfname); 7888 return FALSE; 7889 } 7890 7891 #ifdef BACKSLASH_IN_FILENAME 7892 /* 7893 * Replace all backslashes with forward slashes. This makes the 7894 * autocommand patterns portable between Unix and MS-DOS. 7895 */ 7896 if (sfname != NULL) 7897 forward_slash(sfname); 7898 forward_slash(fname); 7899 #endif 7900 7901 #ifdef VMS 7902 /* remove version for correct match */ 7903 if (sfname != NULL) 7904 vms_remove_version(sfname); 7905 vms_remove_version(fname); 7906 #endif 7907 7908 /* 7909 * Set the name to be used for <amatch>. 7910 */ 7911 autocmd_match = fname; 7912 7913 7914 /* Don't redraw while doing auto commands. */ 7915 ++RedrawingDisabled; 7916 save_sourcing_name = sourcing_name; 7917 sourcing_name = NULL; /* don't free this one */ 7918 save_sourcing_lnum = sourcing_lnum; 7919 sourcing_lnum = 0; /* no line number here */ 7920 7921 #ifdef FEAT_EVAL 7922 save_current_SID = current_SID; 7923 7924 /* Don't use local function variables, if called from a function */ 7925 save_funccalp = save_funccal(); 7926 #endif 7927 7928 /* 7929 * When starting to execute autocommands, save the search patterns. 7930 */ 7931 if (!autocmd_busy) 7932 { 7933 save_search_patterns(); 7934 saveRedobuff(); 7935 did_filetype = keep_filetype; 7936 } 7937 7938 /* 7939 * Note that we are applying autocmds. Some commands need to know. 7940 */ 7941 autocmd_busy = TRUE; 7942 filechangeshell_busy = (event == EVENT_FILECHANGEDSHELL); 7943 ++nesting; /* see matching decrement below */ 7944 7945 /* Remember that FileType was triggered. Used for did_filetype(). */ 7946 if (event == EVENT_FILETYPE) 7947 did_filetype = TRUE; 7948 7949 tail = gettail(fname); 7950 7951 /* Find first autocommand that matches */ 7952 patcmd.curpat = first_autopat[(int)event]; 7953 patcmd.nextcmd = NULL; 7954 patcmd.group = group; 7955 patcmd.fname = fname; 7956 patcmd.sfname = sfname; 7957 patcmd.tail = tail; 7958 patcmd.event = event; 7959 auto_next_pat(&patcmd, FALSE); 7960 7961 /* found one, start executing the autocommands */ 7962 if (patcmd.curpat != NULL) 7963 { 7964 #ifdef FEAT_EVAL 7965 /* set v:cmdarg (only when there is a matching pattern) */ 7966 save_cmdbang = get_vim_var_nr(VV_CMDBANG); 7967 if (eap != NULL) 7968 { 7969 save_cmdarg = set_cmdarg(eap, NULL); 7970 set_vim_var_nr(VV_CMDBANG, (long)eap->forceit); 7971 } 7972 else 7973 save_cmdarg = NULL; /* avoid gcc warning */ 7974 #endif 7975 retval = TRUE; 7976 /* mark the last pattern, to avoid an endless loop when more patterns 7977 * are added when executing autocommands */ 7978 for (ap = patcmd.curpat; ap->next != NULL; ap = ap->next) 7979 ap->last = FALSE; 7980 ap->last = TRUE; 7981 check_lnums(TRUE); /* make sure cursor and topline are valid */ 7982 do_cmdline(NULL, getnextac, (void *)&patcmd, 7983 DOCMD_NOWAIT|DOCMD_VERBOSE|DOCMD_REPEAT); 7984 #ifdef FEAT_EVAL 7985 if (eap != NULL) 7986 { 7987 (void)set_cmdarg(NULL, save_cmdarg); 7988 set_vim_var_nr(VV_CMDBANG, save_cmdbang); 7989 } 7990 #endif 7991 } 7992 7993 --RedrawingDisabled; 7994 autocmd_busy = save_autocmd_busy; 7995 filechangeshell_busy = FALSE; 7996 autocmd_nested = save_autocmd_nested; 7997 vim_free(sourcing_name); 7998 sourcing_name = save_sourcing_name; 7999 sourcing_lnum = save_sourcing_lnum; 8000 autocmd_fname = save_autocmd_fname; 8001 autocmd_bufnr = save_autocmd_bufnr; 8002 autocmd_match = save_autocmd_match; 8003 #ifdef FEAT_EVAL 8004 current_SID = save_current_SID; 8005 restore_funccal(save_funccalp); 8006 #endif 8007 vim_free(fname); 8008 vim_free(sfname); 8009 --nesting; /* see matching increment above */ 8010 8011 /* 8012 * When stopping to execute autocommands, restore the search patterns and 8013 * the redo buffer. 8014 */ 8015 if (!autocmd_busy) 8016 { 8017 restore_search_patterns(); 8018 restoreRedobuff(); 8019 did_filetype = FALSE; 8020 } 8021 8022 /* 8023 * Some events don't set or reset the Changed flag. 8024 * Check if still in the same buffer! 8025 */ 8026 if (curbuf == old_curbuf 8027 && (event == EVENT_BUFREADPOST 8028 || event == EVENT_BUFWRITEPOST 8029 || event == EVENT_FILEAPPENDPOST 8030 || event == EVENT_VIMLEAVE 8031 || event == EVENT_VIMLEAVEPRE)) 8032 { 8033 #ifdef FEAT_TITLE 8034 if (curbuf->b_changed != save_changed) 8035 need_maketitle = TRUE; 8036 #endif 8037 curbuf->b_changed = save_changed; 8038 } 8039 8040 au_cleanup(); /* may really delete removed patterns/commands now */ 8041 return retval; 8042 } 8043 8044 /* 8045 * Find next autocommand pattern that matches. 8046 */ 8047 static void 8048 auto_next_pat(apc, stop_at_last) 8049 AutoPatCmd *apc; 8050 int stop_at_last; /* stop when 'last' flag is set */ 8051 { 8052 AutoPat *ap; 8053 AutoCmd *cp; 8054 char_u *name; 8055 char *s; 8056 8057 vim_free(sourcing_name); 8058 sourcing_name = NULL; 8059 8060 for (ap = apc->curpat; ap != NULL && !got_int; ap = ap->next) 8061 { 8062 apc->curpat = NULL; 8063 8064 /* only use a pattern when it has not been removed, has commands and 8065 * the group matches */ 8066 if (ap->pat != NULL && ap->cmds != NULL 8067 && (apc->group == AUGROUP_ALL || apc->group == ap->group)) 8068 { 8069 if (match_file_pat(ap->reg_pat, apc->fname, apc->sfname, apc->tail, 8070 ap->allow_dirs)) 8071 { 8072 name = event_nr2name(apc->event); 8073 s = _("%s Auto commands for \"%s\""); 8074 sourcing_name = alloc((unsigned)(STRLEN(s) 8075 + STRLEN(name) + ap->patlen + 1)); 8076 if (sourcing_name != NULL) 8077 { 8078 sprintf((char *)sourcing_name, s, 8079 (char *)name, (char *)ap->pat); 8080 if (p_verbose >= 8) 8081 msg_str((char_u *)_("Executing %s"), sourcing_name); 8082 } 8083 8084 apc->curpat = ap; 8085 apc->nextcmd = ap->cmds; 8086 /* mark last command */ 8087 for (cp = ap->cmds; cp->next != NULL; cp = cp->next) 8088 cp->last = FALSE; 8089 cp->last = TRUE; 8090 } 8091 line_breakcheck(); 8092 if (apc->curpat != NULL) /* found a match */ 8093 break; 8094 } 8095 if (stop_at_last && ap->last) 8096 break; 8097 } 8098 } 8099 8100 /* 8101 * Get next autocommand command. 8102 * Called by do_cmdline() to get the next line for ":if". 8103 * Returns allocated string, or NULL for end of autocommands. 8104 */ 8105 /* ARGSUSED */ 8106 static char_u * 8107 getnextac(c, cookie, indent) 8108 int c; /* not used */ 8109 void *cookie; 8110 int indent; /* not used */ 8111 { 8112 AutoPatCmd *acp = (AutoPatCmd *)cookie; 8113 char_u *retval; 8114 AutoCmd *ac; 8115 8116 /* Can be called again after returning the last line. */ 8117 if (acp->curpat == NULL) 8118 return NULL; 8119 8120 /* repeat until we find an autocommand to execute */ 8121 for (;;) 8122 { 8123 /* skip removed commands */ 8124 while (acp->nextcmd != NULL && acp->nextcmd->cmd == NULL) 8125 if (acp->nextcmd->last) 8126 acp->nextcmd = NULL; 8127 else 8128 acp->nextcmd = acp->nextcmd->next; 8129 8130 if (acp->nextcmd != NULL) 8131 break; 8132 8133 /* at end of commands, find next pattern that matches */ 8134 if (acp->curpat->last) 8135 acp->curpat = NULL; 8136 else 8137 acp->curpat = acp->curpat->next; 8138 if (acp->curpat != NULL) 8139 auto_next_pat(acp, TRUE); 8140 if (acp->curpat == NULL) 8141 return NULL; 8142 } 8143 8144 ac = acp->nextcmd; 8145 8146 if (p_verbose >= 9) 8147 { 8148 msg_scroll = TRUE; /* always scroll up, don't overwrite */ 8149 msg_str((char_u *)_("autocommand %s"), ac->cmd); 8150 msg_puts((char_u *)"\n"); /* don't overwrite this either */ 8151 cmdline_row = msg_row; 8152 } 8153 retval = vim_strsave(ac->cmd); 8154 autocmd_nested = ac->nested; 8155 #ifdef FEAT_EVAL 8156 current_SID = ac->scriptID; 8157 #endif 8158 if (ac->last) 8159 acp->nextcmd = NULL; 8160 else 8161 acp->nextcmd = ac->next; 8162 return retval; 8163 } 8164 8165 /* 8166 * Return TRUE if there is a matching autocommand for "fname". 8167 */ 8168 int 8169 has_autocmd(event, sfname) 8170 EVENT_T event; 8171 char_u *sfname; 8172 { 8173 AutoPat *ap; 8174 char_u *fname; 8175 char_u *tail = gettail(sfname); 8176 int retval = FALSE; 8177 8178 fname = FullName_save(sfname, FALSE); 8179 if (fname == NULL) 8180 return FALSE; 8181 8182 #ifdef BACKSLASH_IN_FILENAME 8183 /* 8184 * Replace all backslashes with forward slashes. This makes the 8185 * autocommand patterns portable between Unix and MS-DOS. 8186 */ 8187 sfname = vim_strsave(sfname); 8188 if (sfname != NULL) 8189 forward_slash(sfname); 8190 forward_slash(fname); 8191 #endif 8192 8193 for (ap = first_autopat[(int)event]; ap != NULL; ap = ap->next) 8194 if (ap->pat != NULL && ap->cmds != NULL 8195 && match_file_pat(ap->reg_pat, fname, sfname, tail, 8196 ap->allow_dirs)) 8197 { 8198 retval = TRUE; 8199 break; 8200 } 8201 8202 vim_free(fname); 8203 #ifdef BACKSLASH_IN_FILENAME 8204 vim_free(sfname); 8205 #endif 8206 8207 return retval; 8208 } 8209 8210 #if defined(FEAT_CMDL_COMPL) || defined(PROTO) 8211 /* 8212 * Function given to ExpandGeneric() to obtain the list of autocommand group 8213 * names. 8214 */ 8215 /*ARGSUSED*/ 8216 char_u * 8217 get_augroup_name(xp, idx) 8218 expand_T *xp; 8219 int idx; 8220 { 8221 if (idx == augroups.ga_len) /* add "END" add the end */ 8222 return (char_u *)"END"; 8223 if (idx >= augroups.ga_len) /* end of list */ 8224 return NULL; 8225 if (AUGROUP_NAME(idx) == NULL) /* skip deleted entries */ 8226 return (char_u *)""; 8227 return AUGROUP_NAME(idx); /* return a name */ 8228 } 8229 8230 static int include_groups = FALSE; 8231 8232 char_u * 8233 set_context_in_autocmd(xp, arg, doautocmd) 8234 expand_T *xp; 8235 char_u *arg; 8236 int doautocmd; /* TRUE for :doautocmd, FALSE for :autocmd */ 8237 { 8238 char_u *p; 8239 int group; 8240 8241 /* check for a group name, skip it if present */ 8242 include_groups = FALSE; 8243 p = arg; 8244 group = au_get_grouparg(&arg); 8245 if (group == AUGROUP_ERROR) 8246 return NULL; 8247 /* If there only is a group name that's what we expand. */ 8248 if (*arg == NUL && group != AUGROUP_ALL && !vim_iswhite(arg[-1])) 8249 { 8250 arg = p; 8251 group = AUGROUP_ALL; 8252 } 8253 8254 /* skip over event name */ 8255 for (p = arg; *p != NUL && !vim_iswhite(*p); ++p) 8256 if (*p == ',') 8257 arg = p + 1; 8258 if (*p == NUL) 8259 { 8260 if (group == AUGROUP_ALL) 8261 include_groups = TRUE; 8262 xp->xp_context = EXPAND_EVENTS; /* expand event name */ 8263 xp->xp_pattern = arg; 8264 return NULL; 8265 } 8266 8267 /* skip over pattern */ 8268 arg = skipwhite(p); 8269 while (*arg && (!vim_iswhite(*arg) || arg[-1] == '\\')) 8270 arg++; 8271 if (*arg) 8272 return arg; /* expand (next) command */ 8273 8274 if (doautocmd) 8275 xp->xp_context = EXPAND_FILES; /* expand file names */ 8276 else 8277 xp->xp_context = EXPAND_NOTHING; /* pattern is not expanded */ 8278 return NULL; 8279 } 8280 8281 /* 8282 * Function given to ExpandGeneric() to obtain the list of event names. 8283 */ 8284 /*ARGSUSED*/ 8285 char_u * 8286 get_event_name(xp, idx) 8287 expand_T *xp; 8288 int idx; 8289 { 8290 if (idx < augroups.ga_len) /* First list group names, if wanted */ 8291 { 8292 if (!include_groups || AUGROUP_NAME(idx) == NULL) 8293 return (char_u *)""; /* skip deleted entries */ 8294 return AUGROUP_NAME(idx); /* return a name */ 8295 } 8296 return (char_u *)event_names[idx - augroups.ga_len].name; 8297 } 8298 8299 #endif /* FEAT_CMDL_COMPL */ 8300 8301 /* 8302 * Return TRUE if an autocommand is defined for "event" and "pattern". 8303 * "pattern" can be NULL to accept any pattern. 8304 */ 8305 int 8306 au_exists(name, name_end, pattern) 8307 char_u *name; 8308 char_u *name_end; 8309 char_u *pattern; 8310 { 8311 char_u *event_name; 8312 char_u *p; 8313 EVENT_T event; 8314 AutoPat *ap; 8315 8316 /* find the index (enum) for the event name */ 8317 event_name = vim_strnsave(name, (int)(name_end - name)); 8318 if (event_name == NULL) 8319 return FALSE; 8320 event = event_name2nr(event_name, &p); 8321 vim_free(event_name); 8322 8323 /* return FALSE if the event name is not recognized */ 8324 if (event == NUM_EVENTS) /* unknown event name */ 8325 return FALSE; 8326 8327 /* Find the first autocommand for this event. 8328 * If there isn't any, return FALSE; 8329 * If there is one and no pattern given, return TRUE; */ 8330 ap = first_autopat[(int)event]; 8331 if (ap == NULL) 8332 return FALSE; 8333 if (pattern == NULL) 8334 return TRUE; 8335 8336 /* Check if there is an autocommand with the given pattern. */ 8337 for ( ; ap != NULL; ap = ap->next) 8338 /* only use a pattern when it has not been removed and has commands */ 8339 if (ap->pat != NULL && ap->cmds != NULL 8340 && fnamecmp(ap->pat, pattern) == 0) 8341 return TRUE; 8342 8343 return FALSE; 8344 } 8345 #endif /* FEAT_AUTOCMD */ 8346 8347 #if defined(FEAT_AUTOCMD) || defined(FEAT_WILDIGN) || defined(PROTO) 8348 /* 8349 * Try matching a filename with a pattern. 8350 * Used for autocommands and 'wildignore'. 8351 * Returns TRUE if there is a match, FALSE otherwise. 8352 */ 8353 int 8354 match_file_pat(pattern, fname, sfname, tail, allow_dirs) 8355 char_u *pattern; /* pattern to match with */ 8356 char_u *fname; /* full path of file name */ 8357 char_u *sfname; /* short file name or NULL */ 8358 char_u *tail; /* tail of path */ 8359 int allow_dirs; /* allow matching with dir */ 8360 { 8361 regmatch_T regmatch; 8362 int result = FALSE; 8363 #ifdef FEAT_OSFILETYPE 8364 int no_pattern = FALSE; /* TRUE if check is filetype only */ 8365 char_u *type_start; 8366 char_u c; 8367 int match = FALSE; 8368 #endif 8369 8370 #ifdef CASE_INSENSITIVE_FILENAME 8371 regmatch.rm_ic = TRUE; /* Always ignore case */ 8372 #else 8373 regmatch.rm_ic = FALSE; /* Don't ever ignore case */ 8374 #endif 8375 #ifdef FEAT_OSFILETYPE 8376 if (*pattern == '<') 8377 { 8378 /* There is a filetype condition specified with this pattern. 8379 * Check the filetype matches first. If not, don't bother with the 8380 * pattern (set regprog to NULL). 8381 * Always use magic for the regexp. 8382 */ 8383 8384 for (type_start = pattern + 1; (c = *pattern); pattern++) 8385 { 8386 if ((c == ';' || c == '>') && match == FALSE) 8387 { 8388 *pattern = NUL; /* Terminate the string */ 8389 match = mch_check_filetype(fname, type_start); 8390 *pattern = c; /* Restore the terminator */ 8391 type_start = pattern + 1; 8392 } 8393 if (c == '>') 8394 break; 8395 } 8396 8397 /* (c should never be NUL, but check anyway) */ 8398 if (match == FALSE || c == NUL) 8399 regmatch.regprog = NULL; /* Doesn't match - don't check pat. */ 8400 else if (*pattern == NUL) 8401 { 8402 regmatch.regprog = NULL; /* Vim will try to free regprog later */ 8403 no_pattern = TRUE; /* Always matches - don't check pat. */ 8404 } 8405 else 8406 regmatch.regprog = vim_regcomp(pattern + 1, RE_MAGIC); 8407 } 8408 else 8409 #endif 8410 regmatch.regprog = vim_regcomp(pattern, RE_MAGIC); 8411 8412 /* 8413 * Try for a match with the pattern with: 8414 * 1. the full file name, when the pattern has a '/'. 8415 * 2. the short file name, when the pattern has a '/'. 8416 * 3. the tail of the file name, when the pattern has no '/'. 8417 */ 8418 if ( 8419 #ifdef FEAT_OSFILETYPE 8420 /* If the check is for a filetype only and we don't care 8421 * about the path then skip all the regexp stuff. 8422 */ 8423 no_pattern || 8424 #endif 8425 (regmatch.regprog != NULL 8426 && ((allow_dirs 8427 && (vim_regexec(®match, fname, (colnr_T)0) 8428 || (sfname != NULL 8429 && vim_regexec(®match, sfname, (colnr_T)0)))) 8430 || (!allow_dirs && vim_regexec(®match, tail, (colnr_T)0))))) 8431 result = TRUE; 8432 8433 vim_free(regmatch.regprog); 8434 return result; 8435 } 8436 #endif 8437 8438 #if defined(FEAT_WILDIGN) || defined(PROTO) 8439 /* 8440 * Return TRUE if a file matches with a pattern in "list". 8441 * "list" is a comma-separated list of patterns, like 'wildignore'. 8442 * "sfname" is the short file name or NULL, "ffname" the long file name. 8443 */ 8444 int 8445 match_file_list(list, sfname, ffname) 8446 char_u *list; 8447 char_u *sfname; 8448 char_u *ffname; 8449 { 8450 char_u buf[100]; 8451 char_u *tail; 8452 char_u *regpat; 8453 char allow_dirs; 8454 int match; 8455 char_u *p; 8456 8457 tail = gettail(sfname); 8458 8459 /* try all patterns in 'wildignore' */ 8460 p = list; 8461 while (*p) 8462 { 8463 copy_option_part(&p, buf, 100, ","); 8464 regpat = file_pat_to_reg_pat(buf, NULL, &allow_dirs, FALSE); 8465 if (regpat == NULL) 8466 break; 8467 match = match_file_pat(regpat, ffname, sfname, tail, (int)allow_dirs); 8468 vim_free(regpat); 8469 if (match) 8470 return TRUE; 8471 } 8472 return FALSE; 8473 } 8474 #endif 8475 8476 /* 8477 * Convert the given pattern "pat" which has shell style wildcards in it, into 8478 * a regular expression, and return the result in allocated memory. If there 8479 * is a directory path separator to be matched, then TRUE is put in 8480 * allow_dirs, otherwise FALSE is put there -- webb. 8481 * Handle backslashes before special characters, like "\*" and "\ ". 8482 * 8483 * If FEAT_OSFILETYPE defined then pass initial <type> through unchanged. Eg: 8484 * '<html>myfile' becomes '<html>^myfile$' -- leonard. 8485 * 8486 * Returns NULL when out of memory. 8487 */ 8488 /*ARGSUSED*/ 8489 char_u * 8490 file_pat_to_reg_pat(pat, pat_end, allow_dirs, no_bslash) 8491 char_u *pat; 8492 char_u *pat_end; /* first char after pattern or NULL */ 8493 char *allow_dirs; /* Result passed back out in here */ 8494 int no_bslash; /* Don't use a backward slash as pathsep */ 8495 { 8496 int size; 8497 char_u *endp; 8498 char_u *reg_pat; 8499 char_u *p; 8500 int i; 8501 int nested = 0; 8502 int add_dollar = TRUE; 8503 #ifdef FEAT_OSFILETYPE 8504 int check_length = 0; 8505 #endif 8506 8507 if (allow_dirs != NULL) 8508 *allow_dirs = FALSE; 8509 if (pat_end == NULL) 8510 pat_end = pat + STRLEN(pat); 8511 8512 #ifdef FEAT_OSFILETYPE 8513 /* Find out how much of the string is the filetype check */ 8514 if (*pat == '<') 8515 { 8516 /* Count chars until the next '>' */ 8517 for (p = pat + 1; p < pat_end && *p != '>'; p++) 8518 ; 8519 if (p < pat_end) 8520 { 8521 /* Pattern is of the form <.*>.* */ 8522 check_length = p - pat + 1; 8523 if (p + 1 >= pat_end) 8524 { 8525 /* The 'pattern' is a filetype check ONLY */ 8526 reg_pat = (char_u *)alloc(check_length + 1); 8527 if (reg_pat != NULL) 8528 { 8529 mch_memmove(reg_pat, pat, (size_t)check_length); 8530 reg_pat[check_length] = NUL; 8531 } 8532 return reg_pat; 8533 } 8534 } 8535 /* else: there was no closing '>' - assume it was a normal pattern */ 8536 8537 } 8538 pat += check_length; 8539 size = 2 + check_length; 8540 #else 8541 size = 2; /* '^' at start, '$' at end */ 8542 #endif 8543 8544 for (p = pat; p < pat_end; p++) 8545 { 8546 switch (*p) 8547 { 8548 case '*': 8549 case '.': 8550 case ',': 8551 case '{': 8552 case '}': 8553 case '~': 8554 size += 2; /* extra backslash */ 8555 break; 8556 #ifdef BACKSLASH_IN_FILENAME 8557 case '\\': 8558 case '/': 8559 size += 4; /* could become "[\/]" */ 8560 break; 8561 #endif 8562 default: 8563 size++; 8564 # ifdef FEAT_MBYTE 8565 if (enc_dbcs != 0 && (*mb_ptr2len_check)(p) > 1) 8566 { 8567 ++p; 8568 ++size; 8569 } 8570 # endif 8571 break; 8572 } 8573 } 8574 reg_pat = alloc(size + 1); 8575 if (reg_pat == NULL) 8576 return NULL; 8577 8578 #ifdef FEAT_OSFILETYPE 8579 /* Copy the type check in to the start. */ 8580 if (check_length) 8581 mch_memmove(reg_pat, pat - check_length, (size_t)check_length); 8582 i = check_length; 8583 #else 8584 i = 0; 8585 #endif 8586 8587 if (pat[0] == '*') 8588 while (pat[0] == '*' && pat < pat_end - 1) 8589 pat++; 8590 else 8591 reg_pat[i++] = '^'; 8592 endp = pat_end - 1; 8593 if (*endp == '*') 8594 { 8595 while (endp - pat > 0 && *endp == '*') 8596 endp--; 8597 add_dollar = FALSE; 8598 } 8599 for (p = pat; *p && nested >= 0 && p <= endp; p++) 8600 { 8601 switch (*p) 8602 { 8603 case '*': 8604 reg_pat[i++] = '.'; 8605 reg_pat[i++] = '*'; 8606 break; 8607 case '.': 8608 #ifdef RISCOS 8609 if (allow_dirs != NULL) 8610 *allow_dirs = TRUE; 8611 /* FALLTHROUGH */ 8612 #endif 8613 case '~': 8614 reg_pat[i++] = '\\'; 8615 reg_pat[i++] = *p; 8616 break; 8617 case '?': 8618 #ifdef RISCOS 8619 case '#': 8620 #endif 8621 reg_pat[i++] = '.'; 8622 break; 8623 case '\\': 8624 if (p[1] == NUL) 8625 break; 8626 #ifdef BACKSLASH_IN_FILENAME 8627 if (!no_bslash) 8628 { 8629 /* translate: 8630 * "\x" to "\\x" e.g., "dir\file" 8631 * "\*" to "\\.*" e.g., "dir\*.c" 8632 * "\?" to "\\." e.g., "dir\??.c" 8633 * "\+" to "\+" e.g., "fileX\+.c" 8634 */ 8635 if ((vim_isfilec(p[1]) || p[1] == '*' || p[1] == '?') 8636 && p[1] != '+') 8637 { 8638 reg_pat[i++] = '['; 8639 reg_pat[i++] = '\\'; 8640 reg_pat[i++] = '/'; 8641 reg_pat[i++] = ']'; 8642 if (allow_dirs != NULL) 8643 *allow_dirs = TRUE; 8644 break; 8645 } 8646 } 8647 #endif 8648 if (*++p == '?' 8649 #ifdef BACKSLASH_IN_FILENAME 8650 && no_bslash 8651 #endif 8652 ) 8653 reg_pat[i++] = '?'; 8654 else 8655 if (*p == ',') 8656 reg_pat[i++] = ','; 8657 else 8658 { 8659 if (allow_dirs != NULL && vim_ispathsep(*p) 8660 #ifdef BACKSLASH_IN_FILENAME 8661 && (!no_bslash || *p != '\\') 8662 #endif 8663 ) 8664 *allow_dirs = TRUE; 8665 reg_pat[i++] = '\\'; 8666 reg_pat[i++] = *p; 8667 } 8668 break; 8669 #ifdef BACKSLASH_IN_FILENAME 8670 case '/': 8671 reg_pat[i++] = '['; 8672 reg_pat[i++] = '\\'; 8673 reg_pat[i++] = '/'; 8674 reg_pat[i++] = ']'; 8675 if (allow_dirs != NULL) 8676 *allow_dirs = TRUE; 8677 break; 8678 #endif 8679 case '{': 8680 reg_pat[i++] = '\\'; 8681 reg_pat[i++] = '('; 8682 nested++; 8683 break; 8684 case '}': 8685 reg_pat[i++] = '\\'; 8686 reg_pat[i++] = ')'; 8687 --nested; 8688 break; 8689 case ',': 8690 if (nested) 8691 { 8692 reg_pat[i++] = '\\'; 8693 reg_pat[i++] = '|'; 8694 } 8695 else 8696 reg_pat[i++] = ','; 8697 break; 8698 default: 8699 # ifdef FEAT_MBYTE 8700 if (enc_dbcs != 0 && (*mb_ptr2len_check)(p) > 1) 8701 reg_pat[i++] = *p++; 8702 else 8703 # endif 8704 if (allow_dirs != NULL && vim_ispathsep(*p)) 8705 *allow_dirs = TRUE; 8706 reg_pat[i++] = *p; 8707 break; 8708 } 8709 } 8710 if (add_dollar) 8711 reg_pat[i++] = '$'; 8712 reg_pat[i] = NUL; 8713 if (nested != 0) 8714 { 8715 if (nested < 0) 8716 EMSG(_("E219: Missing {.")); 8717 else 8718 EMSG(_("E220: Missing }.")); 8719 vim_free(reg_pat); 8720 reg_pat = NULL; 8721 } 8722 return reg_pat; 8723 } 8724