Mercurial > vim
changeset 1591:c19f6b8d0393 v7.1.304
updated for version 7.1-304
author | vimboss |
---|---|
date | Thu, 29 May 2008 19:47:13 +0000 |
parents | fe3ec5ea62f7 |
children | e06e177de52a |
files | src/eval.c src/version.c |
diffstat | 2 files changed, 131 insertions(+), 96 deletions(-) [+] |
line wrap: on
line diff
--- a/src/eval.c +++ b/src/eval.c @@ -21068,8 +21068,12 @@ static int shortpath_for_invalid_fname _ static int shortpath_for_partial __ARGS((char_u **fnamep, char_u **bufp, int *fnamelen)); /* - * Get the short pathname of a file. - * Returns 1 on success. *fnamelen is 0 for nonexistent path. + * Get the short path (8.3) for the filename in "fnamep". + * Only works for a valid file name. + * When the path gets longer "fnamep" is changed and the allocated buffer + * is put in "bufp". + * *fnamelen is the length of "fnamep" and set to 0 for a nonexistent path. + * Returns OK on success, FAIL on failure. */ static int get_short_pathname(fnamep, bufp, fnamelen) @@ -21077,36 +21081,44 @@ get_short_pathname(fnamep, bufp, fnamele char_u **bufp; int *fnamelen; { - int l,len; + int l, len; char_u *newbuf; len = *fnamelen; - l = GetShortPathName(*fnamep, *fnamep, len); if (l > len - 1) { /* If that doesn't work (not enough space), then save the string - * and try again with a new buffer big enough - */ + * and try again with a new buffer big enough. */ newbuf = vim_strnsave(*fnamep, l); if (newbuf == NULL) - return 0; + return FAIL; vim_free(*bufp); *fnamep = *bufp = newbuf; - l = GetShortPathName(*fnamep,*fnamep,l+1); - - /* Really should always succeed, as the buffer is big enough */ + /* Really should always succeed, as the buffer is big enough. */ + l = GetShortPathName(*fnamep, *fnamep, l+1); } *fnamelen = l; - return 1; -} - -/* - * Create a short path name. Returns the length of the buffer it needs. - * Doesn't copy over the end of the buffer passed in. + return OK; +} + +/* + * Get the short path (8.3) for the filename in "fname". The converted + * path is returned in "bufp". + * + * Some of the directories specified in "fname" may not exist. This function + * will shorten the existing directories at the beginning of the path and then + * append the remaining non-existing path. + * + * fname - Pointer to the filename to shorten. On return, contains the + * pointer to the shortened pathname + * bufp - Pointer to an allocated buffer for the filename. + * fnamelen - Length of the filename pointed to by fname + * + * Returns OK on success (or nothing done) and FAIL on failure (out of memory). */ static int shortpath_for_invalid_fname(fname, bufp, fnamelen) @@ -21114,85 +21126,106 @@ shortpath_for_invalid_fname(fname, bufp, char_u **bufp; int *fnamelen; { - char_u *s, *p, *pbuf2, *pbuf3; + char_u *short_fname, *save_fname, *pbuf_unused; + char_u *endp, *save_endp; char_u ch; - int len, len2, plen, slen; + int old_len, len; + int new_len, sfx_len; + int retval = OK; /* Make a copy */ - len2 = *fnamelen; - pbuf2 = vim_strnsave(*fname, len2); - pbuf3 = NULL; - - s = pbuf2 + len2 - 1; /* Find the end */ - slen = 1; - plen = len2; - - if (after_pathsep(pbuf2, s + 1)) - { - --s; - ++slen; - --plen; - } - - do - { - /* Go back one path-separator */ - while (s > pbuf2 && !after_pathsep(pbuf2, s + 1)) - { - --s; - ++slen; - --plen; - } - if (s <= pbuf2) - break; - - /* Remember the character that is about to be splatted */ - ch = *s; - *s = 0; /* get_short_pathname requires a null-terminated string */ - - /* Try it in situ */ - p = pbuf2; - if (!get_short_pathname(&p, &pbuf3, &plen)) - { - vim_free(pbuf2); - return -1; - } - *s = ch; /* Preserve the string */ - } while (plen == 0); - - if (plen > 0) - { - /* Remember the length of the new string. */ - *fnamelen = len = plen + slen; + old_len = *fnamelen; + save_fname = vim_strnsave(*fname, old_len); + pbuf_unused = NULL; + short_fname = NULL; + + endp = save_fname + old_len - 1; /* Find the end of the copy */ + save_endp = endp; + + /* + * Try shortening the supplied path till it succeeds by removing one + * directory at a time from the tail of the path. + */ + len = 0; + for (;;) + { + /* go back one path-separator */ + while (endp > save_fname && !after_pathsep(save_fname, endp + 1)) + --endp; + if (endp <= save_fname) + break; /* processed the complete path */ + + /* + * Replace the path separator with a NUL and try to shorten the + * resulting path. + */ + ch = *endp; + *endp = 0; + short_fname = save_fname; + len = STRLEN(short_fname) + 1; + if (get_short_pathname(&short_fname, &pbuf_unused, &len) == FAIL) + { + retval = FAIL; + goto theend; + } + *endp = ch; /* preserve the string */ + + if (len > 0) + break; /* successfully shortened the path */ + + /* failed to shorten the path. Skip the path separator */ + --endp; + } + + if (len > 0) + { + /* + * Succeeded in shortening the path. Now concatenate the shortened + * path with the remaining path at the tail. + */ + + /* Compute the length of the new path. */ + sfx_len = (int)(save_endp - endp) + 1; + new_len = len + sfx_len; + + *fnamelen = new_len; vim_free(*bufp); - if (len > len2) - { - /* If there's not enough space in the currently allocated string, - * then copy it to a buffer big enough. - */ - *fname= *bufp = vim_strnsave(p, len); + if (new_len > old_len) + { + /* There is not enough space in the currently allocated string, + * copy it to a buffer big enough. */ + *fname = *bufp = vim_strnsave(short_fname, new_len); if (*fname == NULL) - return -1; - } - else - { - /* Transfer pbuf2 to being the main buffer (it's big enough) */ - *fname = *bufp = pbuf2; - if (p != pbuf2) - strncpy(*fname, p, plen); - pbuf2 = NULL; - } - /* Concat the next bit */ - strncpy(*fname + plen, s, slen); - (*fname)[len] = '\0'; - } - vim_free(pbuf3); - vim_free(pbuf2); - return 0; + { + retval = FAIL; + goto theend; + } + } + else + { + /* Transfer short_fname to the main buffer (it's big enough), + * unless get_short_pathname() did its work in-place. */ + *fname = *bufp = save_fname; + if (short_fname != save_fname) + vim_strncpy(save_fname, short_fname, len); + save_fname = NULL; + } + + /* concat the not-shortened part of the path */ + vim_strncpy(*fname + len, endp, sfx_len); + (*fname)[new_len] = NUL; + } + +theend: + vim_free(pbuf_unused); + vim_free(save_fname); + + return retval; } /* * Get a pathname for a partial path. + * Returns OK for success, FAIL for failure. */ static int shortpath_for_partial(fnamep, bufp, fnamelen) @@ -21222,8 +21255,8 @@ shortpath_for_partial(fnamep, bufp, fnam len = tflen = (int)STRLEN(tfname); - if (!get_short_pathname(&tfname, &pbuf, &len)) - return -1; + if (get_short_pathname(&tfname, &pbuf, &len) == FAIL) + return FAIL; if (len == 0) { @@ -21232,8 +21265,8 @@ shortpath_for_partial(fnamep, bufp, fnam * there's not a lot of point in guessing what it might be. */ len = tflen; - if (shortpath_for_invalid_fname(&tfname, &pbuf, &len) == -1) - return -1; + if (shortpath_for_invalid_fname(&tfname, &pbuf, &len) == FAIL) + return FAIL; } /* Count the paths backward to find the beginning of the desired string. */ @@ -21257,7 +21290,7 @@ shortpath_for_partial(fnamep, bufp, fnam if (p >= tfname) *p = '~'; else - return -1; + return FAIL; } else ++p; @@ -21268,7 +21301,7 @@ shortpath_for_partial(fnamep, bufp, fnam *bufp = pbuf; *fnamep = p; - return 0; + return OK; } #endif /* WIN3264 */ @@ -21276,7 +21309,7 @@ shortpath_for_partial(fnamep, bufp, fnam * Adjust a filename, according to a string of modifiers. * *fnamep must be NUL terminated when called. When returning, the length is * determined by *fnamelen. - * Returns valid flags. + * Returns VALID_ flags or -1 for failure. * When there is an error, *fnamep is set to NULL. */ int @@ -21488,7 +21521,7 @@ repeat: */ if (!has_fullname && !vim_isAbsName(*fnamep)) { - if (shortpath_for_partial(fnamep, bufp, fnamelen) == -1) + if (shortpath_for_partial(fnamep, bufp, fnamelen) == FAIL) return -1; } else @@ -21498,7 +21531,7 @@ repeat: /* Simple case, already have the full-name * Nearly always shorter, so try first time. */ l = *fnamelen; - if (!get_short_pathname(fnamep, bufp, &l)) + if (get_short_pathname(fnamep, bufp, &l) == FAIL) return -1; if (l == 0) @@ -21506,7 +21539,7 @@ repeat: /* Couldn't find the filename.. search the paths. */ l = *fnamelen; - if (shortpath_for_invalid_fname(fnamep, bufp, &l ) == -1) + if (shortpath_for_invalid_fname(fnamep, bufp, &l) == FAIL) return -1; } *fnamelen = l;