From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: by sourceware.org (Postfix, from userid 2124) id A883A3858413; Mon, 26 Jun 2023 14:47:21 +0000 (GMT) DKIM-Filter: OpenDKIM Filter v2.11.0 sourceware.org A883A3858413 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable From: Nick Clifton To: bfd-cvs@sourceware.org, gdb-cvs@sourceware.org Subject: [binutils-gdb] Synchromize libiberty sources with master version in gcc repository X-Act-Checkin: binutils-gdb X-Git-Author: Nick Clifton X-Git-Refname: refs/heads/master X-Git-Oldrev: 996ff3e8c565a4e9f9d43db7cc73aa061b98cbc0 X-Git-Newrev: 0bbc38601f8f7704c9de8c81bd6d04b4a905ecab Message-Id: <20230626144721.A883A3858413@sourceware.org> Date: Mon, 26 Jun 2023 14:47:21 +0000 (GMT) X-BeenThere: binutils-cvs@sourceware.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Binutils-cvs mailing list List-Unsubscribe: , List-Archive: List-Help: List-Subscribe: , X-List-Received-Date: Mon, 26 Jun 2023 14:47:21 -0000 https://sourceware.org/git/gitweb.cgi?p=3Dbinutils-gdb.git;h=3D0bbc38601f8f= 7704c9de8c81bd6d04b4a905ecab commit 0bbc38601f8f7704c9de8c81bd6d04b4a905ecab Author: Nick Clifton Date: Mon Jun 26 15:47:15 2023 +0100 Synchromize libiberty sources with master version in gcc repository Diff: --- libiberty/ChangeLog | 69 ++++++++++++ libiberty/argv.c | 33 ++---- libiberty/configure | 4 +- libiberty/configure.ac | 4 +- libiberty/cp-demangle.c | 33 +----- libiberty/lrealpath.c | 199 +++++++++++++++++++++++++++++-= ---- libiberty/make-temp-file.c | 1 + libiberty/obstacks.texi | 4 +- libiberty/pex-win32.c | 93 ++++++++++------ libiberty/strstr.c | 15 ++- libiberty/testsuite/demangle-expected | 30 +++++ 11 files changed, 363 insertions(+), 122 deletions(-) diff --git a/libiberty/ChangeLog b/libiberty/ChangeLog index 0e2289d81b7..3424fef99ba 100644 --- a/libiberty/ChangeLog +++ b/libiberty/ChangeLog @@ -1,3 +1,72 @@ +2023-06-15 Marek Polacek + + * configure.ac: Also set shared when enable_host_pie. + * configure: Regenerate. + +2023-06-13 Nathan Sidwell + + * cp-demangle.c (d_print_conversion): Remove incorrect + template instantiation handling. + * testsuite/demangle-expected: Add testcases. + +2023-06-07 Costas Argyris + + * argv.c (writeargv): Constant propagate "0" for "status", + simplifying the code slightly. + +2023-06-06 Costas Argyris + + * argv.c (writeargv): Simplify & remove gotos. + +2023-06-05 Costas Argyris + + * pex-win32.c: fix typos. + +2023-06-05 Costas Argyris + + * pex-win32.c (win32_spawn): Check command line length + and generate a response file if necessary. + (spawn_script): Adjust parameters. + (pex_win32_exec_child): Ditto. + +2023-06-03 Patrick Palka + + PR c++/70790 + * cp-demangle.c (cplus_demangle_operators): Add the noexcept + operator. + (d_print_comp_inner) : Always + print parens around the operand of noexcept too. + * testsuite/demangle-expected: Test noexcept operator + demangling. + +2023-04-02 Jakub Jelinek + + PR other/109306 + * strstr.c: Revert the 2020-11-13 changes. + (strstr): Return s1 if len is 0. + +2023-03-30 Gerald Pfeifer + + * obstacks.texi (Preparing for Obstacks): Remove a (broken) + reference to the Glibc manual. + +2023-03-03 Costas Argyris + + * pex-win32.c (win32_spawn): Fix memory leak of cmdline + buffer and refactor to have cleanup code appear once + for all exit cases. + +2023-02-11 niXman + + * lrealpath.c (lrealpath): try to resolve symlink and + use UNC paths where applicable. + +2023-01-07 LIU Hao + + PR middle-end/108300 + * make-temp-file.c: Define `WIN32_LEAN_AND_MEAN` before . + * pex-win32.c: Likewise. + 2022-11-23 Marek Polacek =20 Revert: diff --git a/libiberty/argv.c b/libiberty/argv.c index a95a10e14ff..c2823d3e4ba 100644 --- a/libiberty/argv.c +++ b/libiberty/argv.c @@ -289,8 +289,8 @@ char **buildargv (const char *input) @deftypefn Extension int writeargv (char * const *@var{argv}, FILE *@var{f= ile}) =20 Write each member of ARGV, handling all necessary quoting, to the file -named by FILE, separated by whitespace. Return 0 on success, non-zero -if an error occurred while writing to FILE. +associated with FILE, separated by whitespace. Return 0 on success, +non-zero if an error occurred while writing to FILE. =20 @end deftypefn =20 @@ -299,8 +299,6 @@ if an error occurred while writing to FILE. int writeargv (char * const *argv, FILE *f) { - int status =3D 0; - if (f =3D=3D NULL) return 1; =20 @@ -314,37 +312,26 @@ writeargv (char * const *argv, FILE *f) =20 if (ISSPACE(c) || c =3D=3D '\\' || c =3D=3D '\'' || c =3D=3D '"') if (EOF =3D=3D fputc ('\\', f)) - { - status =3D 1; - goto done; - } + return 1; =20 if (EOF =3D=3D fputc (c, f)) - { - status =3D 1; - goto done; - } + return 1; + =20 arg++; } =20 /* Write out a pair of quotes for an empty argument. */ if (arg =3D=3D *argv) - if (EOF =3D=3D fputs ("\"\"", f)) - { - status =3D 1; - goto done; - } + if (EOF =3D=3D fputs ("\"\"", f)) + return 1; =20 if (EOF =3D=3D fputc ('\n', f)) - { - status =3D 1; - goto done; - } + return 1; + =20 argv++; } =20 - done: - return status; + return 0; } =20 /* diff --git a/libiberty/configure b/libiberty/configure index 1ccfac9fb11..dd896270dc6 100755 --- a/libiberty/configure +++ b/libiberty/configure @@ -5396,8 +5396,8 @@ case "${enable_shared}" in *) shared=3Dyes ;; esac =20 -# ...unless --enable-host-shared was passed from top-level config: -if [ "${enable_host_shared}" =3D "yes" ]; then +# ...unless --enable-host-{shared,pie} was passed from top-level config: +if [ "${enable_host_shared}" =3D "yes" ] || [ "${enable_host_pie}" =3D "ye= s" ]; then shared=3Dyes fi =20 diff --git a/libiberty/configure.ac b/libiberty/configure.ac index 6c1ff9c6093..0748c592704 100644 --- a/libiberty/configure.ac +++ b/libiberty/configure.ac @@ -245,8 +245,8 @@ case "${enable_shared}" in *) shared=3Dyes ;; esac =20 -# ...unless --enable-host-shared was passed from top-level config: -if [[ "${enable_host_shared}" =3D "yes" ]]; then +# ...unless --enable-host-{shared,pie} was passed from top-level config: +if [[ "${enable_host_shared}" =3D "yes" ]] || [[ "${enable_host_pie}" =3D = "yes" ]]; then shared=3Dyes fi =20 diff --git a/libiberty/cp-demangle.c b/libiberty/cp-demangle.c index f2b36bcad68..3bd303a7544 100644 --- a/libiberty/cp-demangle.c +++ b/libiberty/cp-demangle.c @@ -1947,6 +1947,7 @@ const struct demangle_operator_info cplus_demangle_op= erators[] =3D { "ng", NL ("-"), 1 }, { "nt", NL ("!"), 1 }, { "nw", NL ("new"), 3 }, + { "nx", NL ("noexcept"), 1 }, { "oR", NL ("|=3D"), 2 }, { "oo", NL ("||"), 2 }, { "or", NL ("|"), 2 }, @@ -5836,8 +5837,8 @@ d_print_comp_inner (struct d_print_info *dpi, int opt= ions, if (code && !strcmp (code, "gs")) /* Avoid parens after '::'. */ d_print_comp (dpi, options, operand); - else if (code && !strcmp (code, "st")) - /* Always print parens for sizeof (type). */ + else if (code && (!strcmp (code, "st") || !strcmp (code, "nx"))) + /* Always print parens for sizeof (type) and noexcept(expr). */ { d_append_char (dpi, '('); d_print_comp (dpi, options, operand); @@ -6659,32 +6660,10 @@ d_print_conversion (struct d_print_info *dpi, int o= ptions, dpt.template_decl =3D dpi->current_template; } =20 - if (d_left (dc)->type !=3D DEMANGLE_COMPONENT_TEMPLATE) - { - d_print_comp (dpi, options, d_left (dc)); - if (dpi->current_template !=3D NULL) - dpi->templates =3D dpt.next; - } - else - { - d_print_comp (dpi, options, d_left (d_left (dc))); - - /* For a templated cast operator, we need to remove the template - parameters from scope after printing the operator name, - so we need to handle the template printing here. */ - if (dpi->current_template !=3D NULL) - dpi->templates =3D dpt.next; + d_print_comp (dpi, options, d_left (dc)); =20 - if (d_last_char (dpi) =3D=3D '<') - d_append_char (dpi, ' '); - d_append_char (dpi, '<'); - d_print_comp (dpi, options, d_right (d_left (dc))); - /* Avoid generating two consecutive '>' characters, to avoid - the C++ syntactic ambiguity. */ - if (d_last_char (dpi) =3D=3D '>') - d_append_char (dpi, ' '); - d_append_char (dpi, '>'); - } + if (dpi->current_template !=3D NULL) + dpi->templates =3D dpt.next; } =20 /* Initialize the information structure we use to pass around diff --git a/libiberty/lrealpath.c b/libiberty/lrealpath.c index c662f8fd37e..2578288e8ac 100644 --- a/libiberty/lrealpath.c +++ b/libiberty/lrealpath.c @@ -68,8 +68,135 @@ extern char *canonicalize_file_name (const char *); /* cygwin has realpath, so it won't get here. */=20 # if defined (_WIN32) # define WIN32_LEAN_AND_MEAN -# include /* for GetFullPathName */ -# endif +# include /* for GetFullPathName/GetFinalPathNameByHandle/ + CreateFile/CloseHandle */ +# define WIN32_REPLACE_SLASHES(_ptr, _len) \ + for (unsigned i =3D 0; i !=3D (_len); ++i) \ + if ((_ptr)[i] =3D=3D '\\') (_ptr)[i] =3D '/'; + +# define WIN32_UNC_PREFIX "//?/UNC/" +# define WIN32_UNC_PREFIX_LEN (sizeof(WIN32_UNC_PREFIX)-1) +# define WIN32_IS_UNC_PREFIX(ptr) \ + (0 =3D=3D memcmp(ptr, WIN32_UNC_PREFIX, WIN32_UNC_PREFIX_LEN)) + +# define WIN32_NON_UNC_PREFIX "//?/" +# define WIN32_NON_UNC_PREFIX_LEN (sizeof(WIN32_NON_UNC_PREFIX)-1) +# define WIN32_IS_NON_UNC_PREFIX(ptr) \ + (0 =3D=3D memcmp(ptr, WIN32_NON_UNC_PREFIX, WIN32_NON_UNC_PREFIX_LEN)) + +/* Get full path name without symlinks resolution. + It also converts all forward slashes to back slashes. +*/ +char* get_full_path_name(const char *filename) { + DWORD len; + char *buf, *ptr, *res; + + /* determining the required buffer size. + from the man: `If the lpBuffer buffer is too small to contain + the path, the return value is the size, in TCHARs, of the buffer + that is required to hold the path _and_the_terminating_null_character= _` + */ + len =3D GetFullPathName(filename, 0, NULL, NULL); + + if ( len =3D=3D 0 ) + return strdup(filename); + + buf =3D (char *)malloc(len); + + /* no point to check the result again */ + len =3D GetFullPathName(filename, len, buf, NULL); + buf[len] =3D 0; + + /* replace slashes */ + WIN32_REPLACE_SLASHES(buf, len); + + /* calculate offset based on prefix type */ + len =3D WIN32_IS_UNC_PREFIX(buf) + ? (WIN32_UNC_PREFIX_LEN - 2) + : WIN32_IS_NON_UNC_PREFIX(buf) + ? WIN32_NON_UNC_PREFIX_LEN + : 0 + ; + + ptr =3D buf + len; + if ( WIN32_IS_UNC_PREFIX(buf) ) { + ptr[0] =3D '/'; + ptr[1] =3D '/'; + } + + res =3D strdup(ptr); + + free(buf); + + return res; +} + +# if _WIN32_WINNT >=3D 0x0600 + +/* Get full path name WITH symlinks resolution. + It also converts all forward slashes to back slashes. +*/ +char* get_final_path_name(HANDLE fh) { + DWORD len; + char *buf, *ptr, *res; + + /* determining the required buffer size. + from the man: `If the function fails because lpszFilePath is too + small to hold the string plus the terminating null character, + the return value is the required buffer size, in TCHARs. This + value _includes_the_size_of_the_terminating_null_character_`. + but in my testcase I have path with 26 chars, the function + returns 26 also, ie without the trailing zero-char... + */ + len =3D GetFinalPathNameByHandle( + fh + ,NULL + ,0 + ,FILE_NAME_NORMALIZED | VOLUME_NAME_DOS + ); + + if ( len =3D=3D 0 ) + return NULL; + + len +=3D 1; /* for zero-char */ + buf =3D (char *)malloc(len); + + /* no point to check the result again */ + len =3D GetFinalPathNameByHandle( + fh + ,buf + ,len + ,FILE_NAME_NORMALIZED | VOLUME_NAME_DOS + ); + buf[len] =3D 0; + + /* replace slashes */ + WIN32_REPLACE_SLASHES(buf, len); + + /* calculate offset based on prefix type */ + len =3D WIN32_IS_UNC_PREFIX(buf) + ? (WIN32_UNC_PREFIX_LEN - 2) + : WIN32_IS_NON_UNC_PREFIX(buf) + ? WIN32_NON_UNC_PREFIX_LEN + : 0 + ; + + ptr =3D buf + len; + if ( WIN32_IS_UNC_PREFIX(buf) ) { + ptr[0] =3D '/'; + ptr[1] =3D '/'; + } + + res =3D strdup(ptr); + + free(buf); + + return res; +} + +# endif // _WIN32_WINNT >=3D 0x0600 + +# endif // _WIN32 #endif =20 char * @@ -128,30 +255,52 @@ lrealpath (const char *filename) } #endif =20 - /* The MS Windows method. If we don't have realpath, we assume we - don't have symlinks and just canonicalize to a Windows absolute - path. GetFullPath converts ../ and ./ in relative paths to - absolute paths, filling in current drive if one is not given - or using the current directory of a specified drive (eg, "E:foo"). - It also converts all forward slashes to back slashes. */ + /* The MS Windows method */ #if defined (_WIN32) { - char buf[MAX_PATH]; - char* basename; - DWORD len =3D GetFullPathName (filename, MAX_PATH, buf, &basename); - if (len =3D=3D 0 || len > MAX_PATH - 1) - return strdup (filename); - else - { - /* The file system is case-preserving but case-insensitive, - Canonicalize to lowercase, using the codepage associated - with the process locale. */ - CharLowerBuff (buf, len); - return strdup (buf); - } - } -#endif + char *res; + + /* For Windows Vista and greater */ +#if _WIN32_WINNT >=3D 0x0600 + + /* For some reason the function receives just empty `filename`, but no= t NULL. + What should we do in that case? + According to `strdup()` implementation + (https://elixir.bootlin.com/glibc/latest/source/string/strdup.c) + it will alloc 1 byte even for empty but non NULL string. + OK, will use `strdup()` for that case. + */ + if ( 0 =3D=3D strlen(filename) ) + return strdup(filename); + + HANDLE fh =3D CreateFile( + filename + ,FILE_READ_ATTRIBUTES + ,FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE + ,NULL + ,OPEN_EXISTING + ,FILE_FLAG_BACKUP_SEMANTICS + ,NULL + ); + + if ( fh =3D=3D INVALID_HANDLE_VALUE ) { + res =3D get_full_path_name(filename); + } else { + res =3D get_final_path_name(fh); + CloseHandle(fh); =20 - /* This system is a lost cause, just duplicate the filename. */ - return strdup (filename); + if ( !res ) + res =3D get_full_path_name(filename); + } + +#else + + /* For Windows XP */ + res =3D get_full_path_name(filename); + +#endif // _WIN32_WINNT >=3D 0x0600 + + return res; + } +#endif // _WIN32 } diff --git a/libiberty/make-temp-file.c b/libiberty/make-temp-file.c index fae743f3985..1d2f21d6c5c 100644 --- a/libiberty/make-temp-file.c +++ b/libiberty/make-temp-file.c @@ -37,6 +37,7 @@ Boston, MA 02110-1301, USA. */ #include /* May get R_OK, etc. on some systems. */ #endif #if defined(_WIN32) && !defined(__CYGWIN__) +#define WIN32_LEAN_AND_MEAN #include #endif #if HAVE_SYS_STAT_H diff --git a/libiberty/obstacks.texi b/libiberty/obstacks.texi index b2d2403210b..37d26c90f1b 100644 --- a/libiberty/obstacks.texi +++ b/libiberty/obstacks.texi @@ -172,8 +172,8 @@ The value of this variable is a pointer to a function t= hat @code{obstack} uses when @code{obstack_chunk_alloc} fails to allocate memory. The default action is to print a message and abort. You should supply a function that either calls @code{exit} -(@pxref{Program Termination, , , libc, The GNU C Library Reference Manual}= ) or @code{longjmp} (@pxref{Non-Local -Exits, , , libc, The GNU C Library Reference Manual}) and doesn't return. +(@pxref{Program Termination, , , libc, The GNU C Library Reference Manual}= )=20 +or @code{longjmp} and doesn't return. =20 @smallexample void my_obstack_alloc_failed (void) diff --git a/libiberty/pex-win32.c b/libiberty/pex-win32.c index 5f6b420f7b3..f7fe306036b 100644 --- a/libiberty/pex-win32.c +++ b/libiberty/pex-win32.c @@ -20,6 +20,7 @@ Boston, MA 02110-1301, USA. */ =20 #include "pex-common.h" =20 +#define WIN32_LEAN_AND_MEAN #include =20 #ifdef HAVE_STDLIB_H @@ -350,7 +351,7 @@ argv_to_cmdline (char *const *argv) prevent wasting 2 chars per argument of the CreateProcess 32k char limit. We need only escape embedded double-quotes and immediately preceeding backslash characters. A sequence of backslach characters - that is not follwed by a double quote character will not be + that is not followed by a double quote character will not be escaped. */ needs_quotes =3D 0; for (j =3D 0; argv[i][j]; j++) @@ -365,7 +366,7 @@ argv_to_cmdline (char *const *argv) /* Escape preceeding backslashes. */ for (k =3D j - 1; k >=3D 0 && argv[i][k] =3D=3D '\\'; k--) cmdline_len++; - /* Escape the qote character. */ + /* Escape the quote character. */ cmdline_len++; } } @@ -568,7 +569,8 @@ env_compare (const void *a_ptr, const void *b_ptr) * target is not actually an executable, such as if it is a shell script. = */ =20 static pid_t -win32_spawn (const char *executable, +win32_spawn (struct pex_obj *obj, + const char *executable, BOOL search, char *const *argv, char *const *env, /* array of strings of the form: VAR=3DVALU= E */ @@ -576,14 +578,12 @@ win32_spawn (const char *executable, LPSTARTUPINFO si, LPPROCESS_INFORMATION pi) { - char *full_executable; - char *cmdline; + char *full_executable =3D NULL; + char *cmdline =3D NULL; + pid_t pid =3D (pid_t) -1; char **env_copy; char *env_block =3D NULL; =20 - full_executable =3D NULL; - cmdline =3D NULL; - if (env) { int env_size; @@ -621,13 +621,42 @@ win32_spawn (const char *executable, =20 full_executable =3D find_executable (executable, search); if (!full_executable) - goto error; + goto exit; cmdline =3D argv_to_cmdline (argv); if (!cmdline) - goto error; - =20 - /* Create the child process. */ =20 - if (!CreateProcess (full_executable, cmdline,=20 + goto exit; + /* If cmdline is too large, CreateProcess will fail with a bad + 'No such file or directory' error. Try passing it through a + temporary response file instead. */ + if (strlen (cmdline) > 32767) + { + char *response_file =3D make_temp_file (""); + /* Register the file for deletion by pex_free. */ + ++obj->remove_count; + obj->remove =3D XRESIZEVEC (char *, obj->remove, obj->remove_count); + obj->remove[obj->remove_count - 1] =3D response_file; + int fd =3D pex_win32_open_write (obj, response_file, 0, 0); + if (fd =3D=3D -1) + goto exit; + FILE *f =3D pex_win32_fdopenw (obj, fd, 0); + /* Don't write argv[0] (program name) to the response file. */ + if (writeargv (&argv[1], f)) + { + fclose (f); + goto exit; + } + fclose (f); /* Also closes fd and the underlying OS handle. */ + char *response_arg =3D concat ("@", response_file, NULL); + char *response_argv[3] =3D {argv[0], response_arg, NULL}; + free (cmdline); + cmdline =3D argv_to_cmdline (response_argv); + free (response_arg); + if (!cmdline) + goto exit; + } + =20 + /* Create the child process. */ + if (CreateProcess (full_executable, cmdline, /*lpProcessAttributes=3D*/NULL, /*lpThreadAttributes=3D*/NULL, /*bInheritHandles=3D*/TRUE, @@ -637,33 +666,25 @@ win32_spawn (const char *executable, si, pi)) { - free (env_block); - - free (full_executable); - - return (pid_t) -1; + CloseHandle (pi->hThread); + pid =3D (pid_t) pi->hProcess; } =20 + exit: /* Clean up. */ - CloseHandle (pi->hThread); - free (full_executable); - free (env_block); - - return (pid_t) pi->hProcess; - - error: free (env_block); free (cmdline); free (full_executable); - - return (pid_t) -1; + =20 + return pid; } =20 /* Spawn a script. This simulates the Unix script execution mechanism. This function is called as a fallback if win32_spawn fails. */ =20 static pid_t -spawn_script (const char *executable, char *const *argv, +spawn_script (struct pex_obj *obj, + const char *executable, char *const *argv, char* const *env, DWORD dwCreationFlags, LPSTARTUPINFO si, @@ -713,20 +734,20 @@ spawn_script (const char *executable, char *const *ar= gv, executable =3D strrchr (executable1, '\\') + 1; if (!executable) executable =3D executable1; - pid =3D win32_spawn (executable, TRUE, argv, env, + pid =3D win32_spawn (obj, executable, TRUE, argv, env, dwCreationFlags, si, pi); #else if (strchr (executable1, '\\') =3D=3D NULL) - pid =3D win32_spawn (executable1, TRUE, argv, env, + pid =3D win32_spawn (obj, executable1, TRUE, argv, env, dwCreationFlags, si, pi); else if (executable1[0] !=3D '\\') - pid =3D win32_spawn (executable1, FALSE, argv, env, + pid =3D win32_spawn (obj, executable1, FALSE, argv, env, dwCreationFlags, si, pi); else { const char *newex =3D mingw_rootify (executable1); *avhere =3D newex; - pid =3D win32_spawn (newex, FALSE, argv, env, + pid =3D win32_spawn (obj, newex, FALSE, argv, env, dwCreationFlags, si, pi); if (executable1 !=3D newex) free ((char *) newex); @@ -736,7 +757,7 @@ spawn_script (const char *executable, char *const *argv, if (newex !=3D executable1) { *avhere =3D newex; - pid =3D win32_spawn (newex, FALSE, argv, env, + pid =3D win32_spawn (obj, newex, FALSE, argv, env, dwCreationFlags, si, pi); free ((char *) newex); } @@ -755,7 +776,7 @@ spawn_script (const char *executable, char *const *argv, /* Execute a child. */ =20 static pid_t -pex_win32_exec_child (struct pex_obj *obj ATTRIBUTE_UNUSED, int flags, +pex_win32_exec_child (struct pex_obj *obj, int flags, const char *executable, char * const * argv, char* const* env, int in, int out, int errdes, @@ -851,10 +872,10 @@ pex_win32_exec_child (struct pex_obj *obj ATTRIBUTE_U= NUSED, int flags, si.hStdError =3D stderr_handle; =20 /* Create the child process. */ =20 - pid =3D win32_spawn (executable, (flags & PEX_SEARCH) !=3D 0, + pid =3D win32_spawn (obj, executable, (flags & PEX_SEARCH) !=3D 0, argv, env, dwCreationFlags, &si, &pi); if (pid =3D=3D (pid_t) -1) - pid =3D spawn_script (executable, argv, env, dwCreationFlags, + pid =3D spawn_script (obj, executable, argv, env, dwCreationFlags, &si, &pi); if (pid =3D=3D (pid_t) -1) { diff --git a/libiberty/strstr.c b/libiberty/strstr.c index c6f68495a33..49209e8229f 100644 --- a/libiberty/strstr.c +++ b/libiberty/strstr.c @@ -18,18 +18,23 @@ length, the function returns @var{string}. =20 #include =20 -extern int memcmp (const void *, const void *, size_t); +extern char *strchr (const char *, int); +extern int strncmp (const void *, const void *, size_t); extern size_t strlen (const char *); =20 char * strstr (const char *s1, const char *s2) { + const char *p =3D s1; const size_t len =3D strlen (s2); - while (*s1) + + if (!len) + return s1; + + for (; (p =3D strchr (p, *s2)) !=3D 0; p++) { - if (!memcmp (s1, s2, len)) - return (char *)s1; - ++s1; + if (strncmp (p, s2, len) =3D=3D 0) + return (char *)p; } return (0); } diff --git a/libiberty/testsuite/demangle-expected b/libiberty/testsuite/de= mangle-expected index d9bc7ed4b1f..0acd2d635db 100644 --- a/libiberty/testsuite/demangle-expected +++ b/libiberty/testsuite/demangle-expected @@ -1659,3 +1659,33 @@ auto f()::{lambda(X<$T0>*, X*)#1}= ::operator()(X*, =20 _ZZN1XIiE1FEvENKUliE_clEi X::F()::{lambda(int)#1}::operator()(int) const + +_Z1fIiEv1AIXnxtlT_EEE +void f(A) + +_ZNO1Ycv1XEv +Y::operator X() && + +_ZNO1Ycv1XIT_EIvEEv +Y::operator X() && + +_ZNO1Y3bobEv +Y::bob() && + +_ZNR1Y3bobEv +Y::bob() & + +_ZNKR1YcvRK1XIT_EIvEEv +Y::operator X const&() const & + +_ZZN1XIiEcviEvE1y +X::operator int()::y + +_ZZN1XIiEcv1ZIiEEvE1y +X::operator Z()::y + +_ZZN1Xcv1ZIT_EIiEEvE1y +X::operator Z()::y + +_ZZN1XIfEcv1ZIT_EIiEEvE1y +X::operator Z()::y