Skip to content
This repository

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
tag: v1.5.6-rc0
Fetching contributors…

Cannot retrieve contributors at this time

file 119 lines (91 sloc) 2.29 kb
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119
#include "cache.h"
#include "exec_cmd.h"
#include "quote.h"
#define MAX_ARGS 32

extern char **environ;
static const char *builtin_exec_path = GIT_EXEC_PATH;
static const char *argv_exec_path;

void git_set_argv_exec_path(const char *exec_path)
{
argv_exec_path = exec_path;
}


/* Returns the highest-priority, location to look for git programs. */
const char *git_exec_path(void)
{
const char *env;

if (argv_exec_path)
return argv_exec_path;

env = getenv(EXEC_PATH_ENVIRONMENT);
if (env && *env) {
return env;
}

return builtin_exec_path;
}

static void add_path(struct strbuf *out, const char *path)
{
if (path && *path) {
if (is_absolute_path(path))
strbuf_addstr(out, path);
else
strbuf_addstr(out, make_absolute_path(path));

strbuf_addch(out, ':');
}
}

void setup_path(const char *cmd_path)
{
const char *old_path = getenv("PATH");
struct strbuf new_path;

strbuf_init(&new_path, 0);

add_path(&new_path, argv_exec_path);
add_path(&new_path, getenv(EXEC_PATH_ENVIRONMENT));
add_path(&new_path, builtin_exec_path);
add_path(&new_path, cmd_path);

if (old_path)
strbuf_addstr(&new_path, old_path);
else
strbuf_addstr(&new_path, "/usr/local/bin:/usr/bin:/bin");

setenv("PATH", new_path.buf, 1);

strbuf_release(&new_path);
}

int execv_git_cmd(const char **argv)
{
struct strbuf cmd;
const char *tmp;

strbuf_init(&cmd, 0);
strbuf_addf(&cmd, "git-%s", argv[0]);

/*
* argv[0] must be the git command, but the argv array
* belongs to the caller, and may be reused in
* subsequent loop iterations. Save argv[0] and
* restore it on error.
*/
tmp = argv[0];
argv[0] = cmd.buf;

trace_argv_printf(argv, "trace: exec:");

/* execvp() can only ever return if it fails */
execvp(cmd.buf, (char **)argv);

trace_printf("trace: exec failed: %s\n", strerror(errno));

argv[0] = tmp;

strbuf_release(&cmd);

return -1;
}


int execl_git_cmd(const char *cmd,...)
{
int argc;
const char *argv[MAX_ARGS + 1];
const char *arg;
va_list param;

va_start(param, cmd);
argv[0] = cmd;
argc = 1;
while (argc < MAX_ARGS) {
arg = argv[argc++] = va_arg(param, char *);
if (!arg)
break;
}
va_end(param);
if (MAX_ARGS <= argc)
return error("too many args to run %s", cmd);

argv[argc] = NULL;
return execv_git_cmd(argv);
}
Something went wrong with that request. Please try again.