diff --git a/src/autoload.cpp b/src/autoload.cpp index d4f84a503..a10de1364 100644 --- a/src/autoload.cpp +++ b/src/autoload.cpp @@ -233,7 +233,7 @@ bool autoload_t::locate_file_and_maybe_load_it(const wcstring &cmd, bool really_ if (!has_script_source) { // Iterate over path searching for suitable completion files. - for (size_t i = 0; i < path_list.size(); i++) { + for (size_t i = 0; i < path_list.size() && !found_file; i++) { wcstring next = path_list.at(i); wcstring path = next + L"/" + cmd + L".fish"; @@ -242,7 +242,6 @@ bool autoload_t::locate_file_and_maybe_load_it(const wcstring &cmd, bool really_ continue; } - found_file = true; // Now we're actually going to take the lock. scoped_lock locker(lock); autoload_function_t *func = this->get_node(cmd); @@ -279,7 +278,7 @@ bool autoload_t::locate_file_and_maybe_load_it(const wcstring &cmd, bool really_ // Unconditionally record our access time. func->access = access; - break; + found_file = true; } // If no file or builtin script was found we insert a placeholder function. Later we only diff --git a/src/builtin_string.cpp b/src/builtin_string.cpp index af7cfae27..b19ad38e8 100644 --- a/src/builtin_string.cpp +++ b/src/builtin_string.cpp @@ -685,59 +685,63 @@ class regex_replacer_t : public string_replacer_t { regex(argv0, pattern, opts.ignore_case, streams), replacement(interpret_escapes(replacement_)) {} - bool replace_matches(const wchar_t *arg) { - // A return value of true means all is well (even if no replacements were performed), false - // indicates an unrecoverable error. - if (regex.code == 0) { - // pcre2_compile() failed - return false; - } - - uint32_t options = PCRE2_SUBSTITUTE_OVERFLOW_LENGTH | PCRE2_SUBSTITUTE_EXTENDED | - (opts.all ? PCRE2_SUBSTITUTE_GLOBAL : 0); - size_t arglen = wcslen(arg); - PCRE2_SIZE bufsize = (arglen == 0) ? 16 : 2 * arglen; - wchar_t *output = (wchar_t *)malloc(sizeof(wchar_t) * bufsize); - int pcre2_rc = 0; - for (;;) { - if (output == NULL) { - DIE_MEM(); - } - PCRE2_SIZE outlen = bufsize; - pcre2_rc = pcre2_substitute(regex.code, PCRE2_SPTR(arg), arglen, - 0, // start offset - options, regex.match, - 0, // match context - PCRE2_SPTR(replacement.c_str()), PCRE2_ZERO_TERMINATED, - (PCRE2_UCHAR *)output, &outlen); - - if (pcre2_rc == PCRE2_ERROR_NOMEMORY && bufsize < outlen) { - bufsize = outlen; - // cppcheck-suppress memleakOnRealloc - output = (wchar_t *)realloc(output, sizeof(wchar_t) * bufsize); - continue; - } - break; - } - - bool rc = true; - if (pcre2_rc < 0) { - string_error(streams, _(L"%ls: Regular expression substitute error: %ls\n"), argv0, - pcre2_strerror(pcre2_rc).c_str()); - rc = false; - } else { - if (!opts.quiet) { - streams.out.append(output); - streams.out.append(L'\n'); - } - total_replaced += pcre2_rc; - } - - free(output); - return rc; - } + bool replace_matches(const wchar_t *arg); }; +/// A return value of true means all is well (even if no replacements were performed), false +/// indicates an unrecoverable error. +bool regex_replacer_t::replace_matches(const wchar_t *arg) { + if (regex.code == 0) { + // pcre2_compile() failed + return false; + } + + uint32_t options = PCRE2_SUBSTITUTE_OVERFLOW_LENGTH | PCRE2_SUBSTITUTE_EXTENDED | + (opts.all ? PCRE2_SUBSTITUTE_GLOBAL : 0); + size_t arglen = wcslen(arg); + PCRE2_SIZE bufsize = (arglen == 0) ? 16 : 2 * arglen; + wchar_t *output = (wchar_t *)malloc(sizeof(wchar_t) * bufsize); + int pcre2_rc; + + bool done = false; + while (!done) { + if (output == NULL) { + DIE_MEM(); + } + PCRE2_SIZE outlen = bufsize; + pcre2_rc = pcre2_substitute(regex.code, PCRE2_SPTR(arg), arglen, + 0, // start offset + options, regex.match, + 0, // match context + PCRE2_SPTR(replacement.c_str()), PCRE2_ZERO_TERMINATED, + (PCRE2_UCHAR *)output, &outlen); + + if (pcre2_rc != PCRE2_ERROR_NOMEMORY || bufsize >= outlen) { + done = true; + } else { + bufsize = outlen; + // cppcheck-suppress memleakOnRealloc + output = (wchar_t *)realloc(output, sizeof(wchar_t) * bufsize); + } + } + + bool rc = true; + if (pcre2_rc < 0) { + string_error(streams, _(L"%ls: Regular expression substitute error: %ls\n"), argv0, + pcre2_strerror(pcre2_rc).c_str()); + rc = false; + } else { + if (!opts.quiet) { + streams.out.append(output); + streams.out.append(L'\n'); + } + total_replaced += pcre2_rc; + } + + free(output); + return rc; +} + static int string_replace(parser_t &parser, io_streams_t &streams, int argc, wchar_t **argv) { const wchar_t *short_options = L"aiqr"; const struct woption long_options[] = {{L"all", no_argument, 0, 'a'}, diff --git a/src/parse_tree.cpp b/src/parse_tree.cpp index 407c1dae2..071f51f7c 100644 --- a/src/parse_tree.cpp +++ b/src/parse_tree.cpp @@ -1386,7 +1386,7 @@ const parse_node_t *parse_node_tree_t::find_node_matching_source_location( const parse_node_t *result = NULL; // Find nodes of the given type in the tree, working backwards. const size_t len = this->size(); - for (size_t idx = 0; idx < len; idx++) { + for (size_t idx = 0; idx < len && result == NULL; idx++) { const parse_node_t &node = this->at(idx); // Types must match. @@ -1400,8 +1400,8 @@ const parse_node_t *parse_node_tree_t::find_node_matching_source_location( // Found it. result = &node; - break; } + return result; }