6 #include "run-command.h"
10 static const char push_usage
[] = "git-push [--all] [--tags] [--receive-pack=<git-receive-pack>] [--repo=all] [-f | --force] [-v] [<repository> <refspec>...]";
12 static int all
, force
, thin
= 1, verbose
;
13 static const char *receivepack
;
15 static const char **refspec
;
16 static int refspec_nr
;
18 static void add_refspec(const char *ref
)
20 int nr
= refspec_nr
+ 1;
21 refspec
= xrealloc(refspec
, nr
* sizeof(char *));
26 static void set_refspecs(const char **refs
, int nr
)
29 for (i
= 0; i
< nr
; i
++) {
30 const char *ref
= refs
[i
];
31 if (!strcmp("tag", ref
)) {
35 die("tag shorthand without <tag>");
36 len
= strlen(refs
[i
]) + 11;
38 strcpy(tag
, "refs/tags/");
46 static int do_push(const char *repo
)
52 struct remote
*remote
= remote_get(repo
);
55 die("bad repository '%s'", repo
);
57 if (remote
->receivepack
) {
58 char *rp
= xmalloc(strlen(remote
->receivepack
) + 16);
59 sprintf(rp
, "--receive-pack=%s", remote
->receivepack
);
62 if (!refspec
&& !all
&& remote
->push_refspec_nr
) {
63 refspec
= remote
->push_refspec
;
64 refspec_nr
= remote
->push_refspec_nr
;
67 argv
= xmalloc((refspec_nr
+ 10) * sizeof(char *));
68 argv
[0] = "dummy-send-pack";
71 argv
[argc
++] = "--all";
73 argv
[argc
++] = "--force";
75 argv
[argc
++] = receivepack
;
79 for (i
= 0; i
< remote
->uri_nr
; i
++) {
81 int dest_argc
= common_argc
;
82 int dest_refspec_nr
= refspec_nr
;
83 const char **dest_refspec
= refspec
;
84 const char *dest
= remote
->uri
[i
];
85 const char *sender
= "send-pack";
86 if (!prefixcmp(dest
, "http://") ||
87 !prefixcmp(dest
, "https://"))
90 char *rem
= xmalloc(strlen(remote
->name
) + 10);
91 sprintf(rem
, "--remote=%s", remote
->name
);
92 argv
[dest_argc
++] = rem
;
94 argv
[dest_argc
++] = "--thin";
97 argv
[dest_argc
++] = dest
;
98 while (dest_refspec_nr
--)
99 argv
[dest_argc
++] = *dest_refspec
++;
100 argv
[dest_argc
] = NULL
;
102 fprintf(stderr
, "Pushing to %s\n", dest
);
103 err
= run_command_v_opt(argv
, RUN_GIT_CMD
);
107 error("failed to push to '%s'", remote
->uri
[i
]);
109 case -ERR_RUN_COMMAND_FORK
:
110 error("unable to fork for %s", sender
);
111 case -ERR_RUN_COMMAND_EXEC
:
112 error("unable to exec %s", sender
);
114 case -ERR_RUN_COMMAND_WAITPID
:
115 case -ERR_RUN_COMMAND_WAITPID_WRONG_PID
:
116 case -ERR_RUN_COMMAND_WAITPID_SIGNAL
:
117 case -ERR_RUN_COMMAND_WAITPID_NOEXIT
:
118 error("%s died with strange error", sender
);
125 int cmd_push(int argc
, const char **argv
, const char *prefix
)
128 const char *repo
= NULL
; /* default repository */
130 for (i
= 1; i
< argc
; i
++) {
131 const char *arg
= argv
[i
];
138 if (!strcmp(arg
, "-v")) {
142 if (!prefixcmp(arg
, "--repo=")) {
146 if (!strcmp(arg
, "--all")) {
150 if (!strcmp(arg
, "--tags")) {
151 add_refspec("refs/tags/*");
154 if (!strcmp(arg
, "--force") || !strcmp(arg
, "-f")) {
158 if (!strcmp(arg
, "--thin")) {
162 if (!strcmp(arg
, "--no-thin")) {
166 if (!prefixcmp(arg
, "--receive-pack=")) {
170 if (!prefixcmp(arg
, "--exec=")) {
176 set_refspecs(argv
+ i
, argc
- i
);
180 return do_push(repo
);