diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/nvim/ops.c | 105 | ||||
| -rw-r--r-- | src/nvim/search.c | 4 | 
2 files changed, 69 insertions, 40 deletions
| diff --git a/src/nvim/ops.c b/src/nvim/ops.c index 1ee1ce6ecc..67eb6df1bc 100644 --- a/src/nvim/ops.c +++ b/src/nvim/ops.c @@ -90,10 +90,10 @@ struct block_def {    colnr_T start_char_vcols;       /* number of vcols of pre-block char */  }; -  #ifdef INCLUDE_GENERATED_DECLARATIONS  # include "ops.c.generated.h"  #endif +  /*   * The names of operators.   * IMPORTANT: Index must correspond with defines in vim.h!!! @@ -4704,29 +4704,48 @@ get_reg_contents (    return retval;  } -/* - * Store string "str" in register "name". - * "maxlen" is the maximum number of bytes to use, -1 for all bytes. - * If "must_append" is TRUE, always append to the register.  Otherwise append - * if "name" is an uppercase letter. - * Note: "maxlen" and "must_append" don't work for the "/" register. - * Careful: 'str' is modified, you may have to use a copy! - * If "str" ends in '\n' or '\r', use linewise, otherwise use characterwise. - */ -void write_reg_contents(int name, char_u *str, int maxlen, int must_append) +/// write_reg_contents - store `str` in register `name` +/// +/// @see write_reg_contents_ex +void write_reg_contents(int name, +                        const char_u *str, +                        ssize_t len, +                        int must_append)  { -  write_reg_contents_ex(name, str, maxlen, must_append, MAUTO, 0L); +  write_reg_contents_ex(name, str, len, must_append, MAUTO, 0L);  } -void write_reg_contents_ex(int name, char_u *str, int maxlen, int must_append, int yank_type, long block_len) +/// write_reg_contents_ex - store `str` in register `name` +/// +/// If `str` ends in '\n' or '\r', use linewise, otherwise use +/// characterwise. +/// +/// @warning when `name` is '/', `len` and `must_append` are ignored. This +///          means that `str` MUST be NUL-terminated. +/// +/// @param name The name of the register +/// @param str The contents to write +/// @param len If >= 0, write `len` bytes of `str`. Otherwise, write +///               `strlen(str)` bytes. If `len` is larger than the +///               allocated size of `src`, the behaviour is undefined. +/// @param must_append If true, append the contents of `str` to the current +///                    contents of the register. Note that regardless of +///                    `must_append`, this function will append when `name` +///                    is an uppercase letter. +/// @param yank_type MCHAR, MLINE, MBLOCK or MAUTO +/// @param block_len width of visual block +void write_reg_contents_ex(int name, +                           const char_u *str, +                           ssize_t len, +                           int must_append, +                           int yank_type, +                           long block_len)  {    struct yankreg  *old_y_previous, *old_y_current; -  long len; -  if (maxlen >= 0) -    len = maxlen; -  else -    len = (long)STRLEN(str); +  if (len < 0) { +    len = (ssize_t) STRLEN(str); +  }    /* Special case: '/' search pattern */    if (name == '/') { @@ -4735,17 +4754,25 @@ void write_reg_contents_ex(int name, char_u *str, int maxlen, int must_append, i    }    if (name == '=') { -    char_u      *p, *s; - -    p = vim_strnsave(str, (int)len); +    size_t offset = 0; +    size_t totlen = (size_t) len; -    if (must_append) { -      s = concat_str(get_expr_line_src(), p); -      free(p); -      p = s; +    if (must_append && expr_line) { +      // append has been specified and expr_line already exists, so we'll +      // append the new string to expr_line. +      size_t exprlen = STRLEN(expr_line); +      totlen += exprlen; +      offset = exprlen;      } -    set_expr_line(p); + +    // modify the global expr_line, extend/shrink it if necessary (realloc). +    // Copy the input string into the adjusted memory at the specified +    // offset. +    expr_line = xrealloc(expr_line, totlen + 1); +    memcpy(expr_line + offset, str, (size_t) len); +    expr_line[totlen] = NUL; +      return;    } @@ -4773,18 +4800,20 @@ void write_reg_contents_ex(int name, char_u *str, int maxlen, int must_append, i    y_current = old_y_current;  } -/* - * Put a string into a register.  When the register is not empty, the string - * is appended. - */ -static void  -str_to_reg ( -    struct yankreg *y_ptr,             /* pointer to yank register */ -    int yank_type,                          /* MCHAR, MLINE, MBLOCK, MAUTO */ -    char_u *str,               /* string to put in register */ -    long len,                               /* length of string */ -    long blocklen                          /* width of Visual block */ -) +/// str_to_reg - Put a string into a register. +/// +/// When the register is not empty, the string is appended. +/// +/// @param y_ptr pointer to yank register +/// @param yank_type MCHAR, MLINE, MBLOCK or MAUTO +/// @param str string to put in register +/// @param len length of the string +/// @param blocklen width of visual block +static void str_to_reg(struct yankreg *y_ptr, +                       int yank_type, +                       const char_u *str, +                       long len, +                       long blocklen)  {    int type;                             /* MCHAR, MLINE or MBLOCK */    int lnum; diff --git a/src/nvim/search.c b/src/nvim/search.c index 5ba30eeb00..08fdfa4b63 100644 --- a/src/nvim/search.c +++ b/src/nvim/search.c @@ -375,14 +375,14 @@ void reset_search_dir(void)   * Set the last search pattern.  For ":let @/ =" and viminfo.   * Also set the saved search pattern, so that this works in an autocommand.   */ -void set_last_search_pat(char_u *s, int idx, int magic, int setlast) +void set_last_search_pat(const char_u *s, int idx, int magic, int setlast)  {    free(spats[idx].pat);    /* An empty string means that nothing should be matched. */    if (*s == NUL)      spats[idx].pat = NULL;    else -    spats[idx].pat = vim_strsave(s); +    spats[idx].pat = (char_u *) xstrdup((char *) s);    spats[idx].magic = magic;    spats[idx].no_scs = FALSE;    spats[idx].off.dir = '/'; | 
