{"thread":{"id":"10387","subject":"[PATCH] When exec'ing sub-commands, fall back on execvp (the PATH)","startedAt":"2007-10-20T06:44:59Z","lastAt":"2007-10-20T07:30:54Z","messageCount":2,"participants":["Scott Parish","Johannes Schindelin"],"isPatch":true,"patchVersion":1,"patchTotal":null},"messages":[{"id":"56668","messageId":"20071020064459.GB2237@srparish.net","threadId":"10387","inReplyTo":null,"subject":"[PATCH] When exec'ing sub-commands, fall back on execvp (the PATH)","fromName":"Scott Parish","fromEmail":"srp@srparish.net","sentAt":"2007-10-20T06:44:59Z","receivedAt":"2007-10-20T06:44:59Z","isPatch":true,"sender":{"key":"srp@srparish.net","avatar":"https://gravatar.com/avatar/870e5b6fc4f710cf4db5684bd9af7f2cee5734b3dab3209b13e00cf64f6c9f0e?d=mp&s=160"},"body":" Signed-off-by: Scott R Parish <srp@srparish.net>\n\n---\n exec_cmd.c |   26 ++++++++++++++++++++++----\n 1 files changed, 22 insertions(+), 4 deletions(-)\n\ndiff --git a/exec_cmd.c b/exec_cmd.c\nindex 9b74ed2..674c9f3 100644\n--- a/exec_cmd.c\n+++ b/exec_cmd.c\n@@ -34,15 +34,15 @@ int execv_git_cmd(const char **argv)\n {\n \tchar git_command[PATH_MAX + 1];\n \tint i;\n+\tint rc;\n \tconst char *paths[] = { current_exec_path,\n \t\t\t\tgetenv(EXEC_PATH_ENVIRONMENT),\n \t\t\t\tbuiltin_exec_path };\n+\tconst char *tmp;\n+\tsize_t len;\n \n \tfor (i = 0; i < ARRAY_SIZE(paths); ++i) {\n-\t\tsize_t len;\n-\t\tint rc;\n \t\tconst char *exec_dir = paths[i];\n-\t\tconst char *tmp;\n \n \t\tif (!exec_dir || !*exec_dir) continue;\n \n@@ -106,8 +106,26 @@ int execv_git_cmd(const char **argv)\n \n \t\targv[0] = tmp;\n \t}\n-\treturn -1;\n \n+\trc = snprintf(git_command, sizeof(git_command), \"git-%s\", argv[0]);\n+\tif (rc < 0 || rc >= sizeof(git_command) - len) {\n+\t\tfprintf(stderr, \"git: command name given is too long.\\n\");\n+\t\treturn -1;\n+\t}\n+\n+\ttmp = argv[0];\n+\targv[0] = git_command;\n+\n+\ttrace_argv_printf(argv, -1, \"trace: exec:\");\n+\n+\t/* execve() can only ever return if it fails */\n+\texecvp(git_command, (char **)argv);\n+\n+\ttrace_printf(\"trace: exec failed: %s\\n\", strerror(errno));\n+\n+\targv[0] = tmp;\n+\n+\treturn -1;\n }\n \n \n-- \n1.5.3.GIT\n"},{"id":"56675","messageId":"Pine.LNX.4.64.0710200824270.25221@racer.site","threadId":"10387","inReplyTo":"20071020064459.GB2237@srparish.net","subject":"Re: [PATCH] When exec'ing sub-commands, fall back on execvp (the PATH)","fromName":"Johannes Schindelin","fromEmail":"johannes.schindelin@gmx.de","sentAt":"2007-10-20T07:30:54Z","receivedAt":"2007-10-20T07:30:54Z","isPatch":true,"sender":{"key":"johannes.schindelin@gmx.de","avatar":"https://avatars.githubusercontent.com/u/127790?v=4"},"body":"Hi,\n\nOn Fri, 19 Oct 2007, Scott Parish wrote:\n\n> diff --git a/exec_cmd.c b/exec_cmd.c\n> index 9b74ed2..674c9f3 100644\n> --- a/exec_cmd.c\n> +++ b/exec_cmd.c\n> @@ -34,15 +34,15 @@ int execv_git_cmd(const char **argv)\n>  {\n>  \tchar git_command[PATH_MAX + 1];\n>  \tint i;\n> +\tint rc;\n>  \tconst char *paths[] = { current_exec_path,\n>  \t\t\t\tgetenv(EXEC_PATH_ENVIRONMENT),\n>  \t\t\t\tbuiltin_exec_path };\n> +\tconst char *tmp;\n> +\tsize_t len;\n>  \n>  \tfor (i = 0; i < ARRAY_SIZE(paths); ++i) {\n> -\t\tsize_t len;\n> -\t\tint rc;\n>  \t\tconst char *exec_dir = paths[i];\n> -\t\tconst char *tmp;\n>  \n>  \t\tif (!exec_dir || !*exec_dir) continue;\n>  \n> @@ -106,8 +106,26 @@ int execv_git_cmd(const char **argv)\n>  \n>  \t\targv[0] = tmp;\n>  \t}\n> -\treturn -1;\n>  \n> +\trc = snprintf(git_command, sizeof(git_command), \"git-%s\", argv[0]);\n> +\tif (rc < 0 || rc >= sizeof(git_command) - len) {\n> +\t\tfprintf(stderr, \"git: command name given is too long.\\n\");\n> +\t\treturn -1;\n> +\t}\n> +\n> +\ttmp = argv[0];\n> +\targv[0] = git_command;\n> +\n> +\ttrace_argv_printf(argv, -1, \"trace: exec:\");\n> +\n> +\t/* execve() can only ever return if it fails */\n> +\texecvp(git_command, (char **)argv);\n> +\n> +\ttrace_printf(\"trace: exec failed: %s\\n\", strerror(errno));\n> +\n> +\targv[0] = tmp;\n> +\n> +\treturn -1;\n>  }\n\nI am not sure that this is elegant enough: Something like this (completely \nuntested) might be better:\n\ndiff --git a/exec_cmd.c b/exec_cmd.c\nindex 9b74ed2..c928f37 100644\n--- a/exec_cmd.c\n+++ b/exec_cmd.c\n@@ -36,7 +36,8 @@ int execv_git_cmd(const char **argv)\n \tint i;\n \tconst char *paths[] = { current_exec_path,\n \t\t\t\tgetenv(EXEC_PATH_ENVIRONMENT),\n-\t\t\t\tbuiltin_exec_path };\n+\t\t\t\tbuiltin_exec_path,\n+\t\t\t\t\"\" };\n \n \tfor (i = 0; i < ARRAY_SIZE(paths); ++i) {\n \t\tsize_t len;\n@@ -44,9 +45,12 @@ int execv_git_cmd(const char **argv)\n \t\tconst char *exec_dir = paths[i];\n \t\tconst char *tmp;\n \n-\t\tif (!exec_dir || !*exec_dir) continue;\n+\t\tif (!exec_dir) continue;\n \n-\t\tif (*exec_dir != '/') {\n+\t\tif (!*exec_dir)\n+\t\t\t/* try PATH */\n+\t\t\t*git_command = '\\0';\n+\t\telse if (*exec_dir != '/') {\n \t\t\tif (!getcwd(git_command, sizeof(git_command))) {\n \t\t\t\tfprintf(stderr, \"git: cannot determine \"\n \t\t\t\t\t\"current directory: %s\\n\",\n@@ -81,7 +85,7 @@ int execv_git_cmd(const char **argv)\n \n \t\tlen = strlen(git_command);\n \t\trc = snprintf(git_command + len, sizeof(git_command) - len,\n-\t\t\t      \"/git-%s\", argv[0]);\n+\t\t\t      \"%sgit-%s\", *exec_dir ? \"/\" : \"\", argv[0]);\n \t\tif (rc < 0 || rc >= sizeof(git_command) - len) {\n \t\t\tfprintf(stderr,\n \t\t\t\t\"git: command name given is too long.\\n\");\n\nCiao,\nDscho\n"}]}