]> rtime.felk.cvut.cz Git - git.git/commitdiff
Merge branch 'js/run-command-updates'
authorJunio C Hamano <gitster@pobox.com>
Tue, 11 Aug 2009 05:14:57 +0000 (22:14 -0700)
committerJunio C Hamano <gitster@pobox.com>
Tue, 11 Aug 2009 05:14:57 +0000 (22:14 -0700)
* js/run-command-updates:
  api-run-command.txt: describe error behavior of run_command functions
  run-command.c: squelch a "use before assignment" warning
  receive-pack: remove unnecessary run_status report
  run_command: report failure to execute the program, but optionally don't
  run_command: encode deadly signal number in the return value
  run_command: report system call errors instead of returning error codes
  run_command: return exit code as positive value
  MinGW: simplify waitpid() emulation macros

1  2 
builtin-merge.c
git.c
ll-merge.c
run-command.c
t/t5530-upload-pack-error.sh
transport.c

diff --combined builtin-merge.c
index 82b546689c500649285ea2c7825171f572c3758e,96ecaf4e484639c844d48884ae2fd559d5e9a352..0b12fb31558d1cb59f9e2a8ab049ea944fe3060e
@@@ -268,7 -268,7 +268,7 @@@ static void squash_message(void
        printf("Squash commit -- not updating HEAD\n");
        fd = open(git_path("SQUASH_MSG"), O_WRONLY | O_CREAT, 0666);
        if (fd < 0)
 -              die("Could not write to %s", git_path("SQUASH_MSG"));
 +              die_errno("Could not write to '%s'", git_path("SQUASH_MSG"));
  
        init_revisions(&rev, NULL);
        rev.ignore_merges = 1;
                        NULL, NULL, rev.date_mode, 0);
        }
        if (write(fd, out.buf, out.len) < 0)
 -              die("Writing SQUASH_MSG: %s", strerror(errno));
 +              die_errno("Writing SQUASH_MSG");
        if (close(fd))
 -              die("Finishing SQUASH_MSG: %s", strerror(errno));
 +              die_errno("Finishing SQUASH_MSG");
        strbuf_release(&out);
  }
  
@@@ -428,8 -428,8 +428,8 @@@ static void merge_name(const char *remo
  
                fp = fopen(git_path("FETCH_HEAD"), "r");
                if (!fp)
 -                      die("could not open %s for reading: %s",
 -                              git_path("FETCH_HEAD"), strerror(errno));
 +                      die_errno("could not open '%s' for reading",
 +                                git_path("FETCH_HEAD"));
                strbuf_getline(&line, fp, '\n');
                fclose(fp);
                ptr = strstr(line.buf, "\tnot-for-merge\t");
@@@ -594,7 -594,7 +594,7 @@@ static int try_merge_strategy(const cha
                discard_cache();
                if (read_cache() < 0)
                        die("failed to read the cache");
-               return -ret;
+               return ret;
        }
  }
  
@@@ -764,8 -764,7 +764,8 @@@ static int suggest_conflicts(void
  
        fp = fopen(git_path("MERGE_MSG"), "a");
        if (!fp)
 -              die("Could not open %s for writing", git_path("MERGE_MSG"));
 +              die_errno("Could not open '%s' for writing",
 +                        git_path("MERGE_MSG"));
        fprintf(fp, "\nConflicts:\n");
        for (pos = 0; pos < active_nr; pos++) {
                struct cache_entry *ce = active_cache[pos];
@@@ -1190,29 -1189,27 +1190,29 @@@ int cmd_merge(int argc, const char **ar
                                sha1_to_hex(j->item->object.sha1));
                fd = open(git_path("MERGE_HEAD"), O_WRONLY | O_CREAT, 0666);
                if (fd < 0)
 -                      die("Could open %s for writing",
 -                              git_path("MERGE_HEAD"));
 +                      die_errno("Could not open '%s' for writing",
 +                                git_path("MERGE_HEAD"));
                if (write_in_full(fd, buf.buf, buf.len) != buf.len)
 -                      die("Could not write to %s", git_path("MERGE_HEAD"));
 +                      die_errno("Could not write to '%s'", git_path("MERGE_HEAD"));
                close(fd);
                strbuf_addch(&merge_msg, '\n');
                fd = open(git_path("MERGE_MSG"), O_WRONLY | O_CREAT, 0666);
                if (fd < 0)
 -                      die("Could open %s for writing", git_path("MERGE_MSG"));
 +                      die_errno("Could not open '%s' for writing",
 +                                git_path("MERGE_MSG"));
                if (write_in_full(fd, merge_msg.buf, merge_msg.len) !=
                        merge_msg.len)
 -                      die("Could not write to %s", git_path("MERGE_MSG"));
 +                      die_errno("Could not write to '%s'", git_path("MERGE_MSG"));
                close(fd);
                fd = open(git_path("MERGE_MODE"), O_WRONLY | O_CREAT | O_TRUNC, 0666);
                if (fd < 0)
 -                      die("Could open %s for writing", git_path("MERGE_MODE"));
 +                      die_errno("Could not open '%s' for writing",
 +                                git_path("MERGE_MODE"));
                strbuf_reset(&buf);
                if (!allow_fast_forward)
                        strbuf_addf(&buf, "no-ff");
                if (write_in_full(fd, buf.buf, buf.len) != buf.len)
 -                      die("Could not write to %s", git_path("MERGE_MODE"));
 +                      die_errno("Could not write to '%s'", git_path("MERGE_MODE"));
                close(fd);
        }
  
diff --combined git.c
index 807d875ae06ce7bbf61bb846c5b4cb5a51855eba,18240280e8383a73e575ff0fc519dcfa6bf1db42..4588a8bac21a12240c84eac4b24d68cb72920d80
--- 1/git.c
--- 2/git.c
+++ b/git.c
@@@ -199,7 -199,7 +199,7 @@@ static int handle_alias(int *argcp, con
        }
  
        if (subdir && chdir(subdir))
 -              die("Cannot change to %s: %s", subdir, strerror(errno));
 +              die_errno("Cannot change to '%s'", subdir);
  
        errno = saved_errno;
  
@@@ -256,11 -256,11 +256,11 @@@ static int run_builtin(struct cmd_struc
  
        /* Check for ENOSPC and EIO errors.. */
        if (fflush(stdout))
 -              die("write failure on standard output: %s", strerror(errno));
 +              die_errno("write failure on standard output");
        if (ferror(stdout))
                die("unknown write failure on standard output");
        if (fclose(stdout))
 -              die("close failed on standard output: %s", strerror(errno));
 +              die_errno("close failed on standard output");
        return 0;
  }
  
@@@ -416,13 -416,9 +416,9 @@@ static void execv_dashed_external(cons
         * if we fail because the command is not found, it is
         * OK to return. Otherwise, we just pass along the status code.
         */
-       status = run_command_v_opt(argv, 0);
-       if (status != -ERR_RUN_COMMAND_EXEC) {
-               if (IS_RUN_COMMAND_ERR(status))
-                       die("unable to run '%s'", argv[0]);
-               exit(-status);
-       }
-       errno = ENOENT; /* as if we called execvp */
+       status = run_command_v_opt(argv, RUN_SILENT_EXEC_FAILURE);
+       if (status >= 0 || errno != ENOENT)
+               exit(status);
  
        argv[0] = tmp;
  
diff --combined ll-merge.c
index 0571564ddfb336247c8268fbdecd8674d8bacd3e,31c74578f6b82d859e038ddf9ca43d3b5fd9429a..2d6b6d6cb1d2bc2d334bf058feb3444e94b5a781
@@@ -152,7 -152,7 +152,7 @@@ static void create_temp(mmfile_t *src, 
        strcpy(path, ".merge_file_XXXXXX");
        fd = xmkstemp(path);
        if (write_in_full(fd, src->ptr, src->size) != src->size)
 -              die("unable to write temp-file");
 +              die_errno("unable to write temp-file");
        close(fd);
  }
  
@@@ -192,10 -192,6 +192,6 @@@ static int ll_ext_merge(const struct ll
  
        args[2] = cmd.buf;
        status = run_command_v_opt(args, 0);
-       if (status < -ERR_RUN_COMMAND_FORK)
-               ; /* failure in run-command */
-       else
-               status = -status;
        fd = open(temp[1], O_RDONLY);
        if (fd < 0)
                goto bad;
diff --combined run-command.c
index ff3d8e2d8bf3208b7ad0f29d7cf76cc84a4ad0e6,71f83368c4e97357c782658135982e89c13ae414..f3e7abb7de799a14a8f792195992c4d9d1495c6f
@@@ -19,6 -19,7 +19,7 @@@ int start_command(struct child_process 
  {
        int need_in, need_out, need_err;
        int fdin[2], fdout[2], fderr[2];
+       int failed_errno = failed_errno;
  
        /*
         * In case of errors we must keep the promise to close FDs
        need_in = !cmd->no_stdin && cmd->in < 0;
        if (need_in) {
                if (pipe(fdin) < 0) {
+                       failed_errno = errno;
                        if (cmd->out > 0)
                                close(cmd->out);
-                       return -ERR_RUN_COMMAND_PIPE;
+                       goto fail_pipe;
                }
                cmd->in = fdin[1];
        }
                && cmd->out < 0;
        if (need_out) {
                if (pipe(fdout) < 0) {
+                       failed_errno = errno;
                        if (need_in)
                                close_pair(fdin);
                        else if (cmd->in)
                                close(cmd->in);
-                       return -ERR_RUN_COMMAND_PIPE;
+                       goto fail_pipe;
                }
                cmd->out = fdout[0];
        }
@@@ -52,6 -55,7 +55,7 @@@
        need_err = !cmd->no_stderr && cmd->err < 0;
        if (need_err) {
                if (pipe(fderr) < 0) {
+                       failed_errno = errno;
                        if (need_in)
                                close_pair(fdin);
                        else if (cmd->in)
                                close_pair(fdout);
                        else if (cmd->out)
                                close(cmd->out);
-                       return -ERR_RUN_COMMAND_PIPE;
+ fail_pipe:
+                       error("cannot create pipe for %s: %s",
+                               cmd->argv[0], strerror(failed_errno));
+                       errno = failed_errno;
+                       return -1;
                }
                cmd->err = fderr[0];
        }
                }
  
                if (cmd->dir && chdir(cmd->dir))
 -                      die("exec %s: cd to %s failed (%s)", cmd->argv[0],
 -                          cmd->dir, strerror(errno));
 +                      die_errno("exec '%s': cd to '%s' failed", cmd->argv[0],
 +                          cmd->dir);
                if (cmd->env) {
                        for (; *cmd->env; cmd->env++) {
                                if (strchr(*cmd->env, '='))
                                strerror(errno));
                exit(127);
        }
+       if (cmd->pid < 0)
+               error("cannot fork() for %s: %s", cmd->argv[0],
+                       strerror(failed_errno = errno));
  #else
        int s0 = -1, s1 = -1, s2 = -1;  /* backups of stdin, stdout, stderr */
        const char **sargv = cmd->argv;
        }
  
        cmd->pid = mingw_spawnvpe(cmd->argv[0], cmd->argv, env);
+       failed_errno = errno;
+       if (cmd->pid < 0 && (!cmd->silent_exec_failure || errno != ENOENT))
+               error("cannot spawn %s: %s", cmd->argv[0], strerror(errno));
  
        if (cmd->env)
                free_environ(env);
  #endif
  
        if (cmd->pid < 0) {
-               int err = errno;
                if (need_in)
                        close_pair(fdin);
                else if (cmd->in)
                        close(cmd->out);
                if (need_err)
                        close_pair(fderr);
-               return err == ENOENT ?
-                       -ERR_RUN_COMMAND_EXEC :
-                       -ERR_RUN_COMMAND_FORK;
+               errno = failed_errno;
+               return -1;
        }
  
        if (need_in)
        return 0;
  }
  
- static int wait_or_whine(pid_t pid)
+ static int wait_or_whine(pid_t pid, const char *argv0, int silent_exec_failure)
  {
-       for (;;) {
-               int status, code;
-               pid_t waiting = waitpid(pid, &status, 0);
-               if (waiting < 0) {
-                       if (errno == EINTR)
-                               continue;
-                       error("waitpid failed (%s)", strerror(errno));
-                       return -ERR_RUN_COMMAND_WAITPID;
-               }
-               if (waiting != pid)
-                       return -ERR_RUN_COMMAND_WAITPID_WRONG_PID;
-               if (WIFSIGNALED(status))
-                       return -ERR_RUN_COMMAND_WAITPID_SIGNAL;
-               if (!WIFEXITED(status))
-                       return -ERR_RUN_COMMAND_WAITPID_NOEXIT;
+       int status, code = -1;
+       pid_t waiting;
+       int failed_errno = 0;
+       while ((waiting = waitpid(pid, &status, 0)) < 0 && errno == EINTR)
+               ;       /* nothing */
+       if (waiting < 0) {
+               failed_errno = errno;
+               error("waitpid for %s failed: %s", argv0, strerror(errno));
+       } else if (waiting != pid) {
+               error("waitpid is confused (%s)", argv0);
+       } else if (WIFSIGNALED(status)) {
+               code = WTERMSIG(status);
+               error("%s died of signal %d", argv0, code);
+               /*
+                * This return value is chosen so that code & 0xff
+                * mimics the exit code that a POSIX shell would report for
+                * a program that died from this signal.
+                */
+               code -= 128;
+       } else if (WIFEXITED(status)) {
                code = WEXITSTATUS(status);
-               switch (code) {
-               case 127:
-                       return -ERR_RUN_COMMAND_EXEC;
-               case 0:
-                       return 0;
-               default:
-                       return -code;
+               /*
+                * Convert special exit code when execvp failed.
+                */
+               if (code == 127) {
+                       code = -1;
+                       failed_errno = ENOENT;
+                       if (!silent_exec_failure)
+                               error("cannot run %s: %s", argv0,
+                                       strerror(ENOENT));
                }
+       } else {
+               error("waitpid is confused (%s)", argv0);
        }
+       errno = failed_errno;
+       return code;
  }
  
  int finish_command(struct child_process *cmd)
  {
-       return wait_or_whine(cmd->pid);
+       return wait_or_whine(cmd->pid, cmd->argv[0], cmd->silent_exec_failure);
  }
  
  int run_command(struct child_process *cmd)
@@@ -274,6 -297,7 +297,7 @@@ static void prepare_run_command_v_opt(s
        cmd->no_stdin = opt & RUN_COMMAND_NO_STDIN ? 1 : 0;
        cmd->git_cmd = opt & RUN_GIT_CMD ? 1 : 0;
        cmd->stdout_to_stderr = opt & RUN_COMMAND_STDOUT_TO_STDERR ? 1 : 0;
+       cmd->silent_exec_failure = opt & RUN_SILENT_EXEC_FAILURE ? 1 : 0;
  }
  
  int run_command_v_opt(const char **argv, int opt)
@@@ -338,10 -362,7 +362,7 @@@ int start_async(struct async *async
  int finish_async(struct async *async)
  {
  #ifndef __MINGW32__
-       int ret = 0;
-       if (wait_or_whine(async->pid))
-               ret = error("waitpid (async) failed");
+       int ret = wait_or_whine(async->pid, "child process", 0);
  #else
        DWORD ret = 0;
        if (WaitForSingleObject(async->tid, INFINITE) != WAIT_OBJECT_0)
@@@ -385,15 -406,7 +406,7 @@@ int run_hook(const char *index_file, co
                hook.env = env;
        }
  
-       ret = start_command(&hook);
+       ret = run_command(&hook);
        free(argv);
-       if (ret) {
-               warning("Could not spawn %s", argv[0]);
-               return ret;
-       }
-       ret = finish_command(&hook);
-       if (ret == -ERR_RUN_COMMAND_WAITPID_SIGNAL)
-               warning("%s exited due to uncaught signal", argv[0]);
        return ret;
  }
index 757cc19ecce127ddd0cbf528f7678c2940ac1519,82ca3003dd2cd3c15b10280690e9ac829dc7c1eb..a696b8791b7caa44ae2bd16d6970a791f3a28d3d
@@@ -30,12 -30,11 +30,12 @@@ test_expect_success 'fsck fails' 
        test_must_fail git fsck
  '
  
 -test_expect_success 'upload-pack fails due to error in pack-objects' '
 +test_expect_success 'upload-pack fails due to error in pack-objects packing' '
  
        ! echo "0032want $(git rev-parse HEAD)
  00000009done
  0000" | git upload-pack . > /dev/null 2> output.err &&
 +      grep "unable to read" output.err &&
        grep "pack-objects died" output.err
  '
  
@@@ -52,20 -51,14 +52,23 @@@ test_expect_success 'fsck fails' 
  test_expect_success 'upload-pack fails due to error in rev-list' '
  
        ! echo "0032want $(git rev-parse HEAD)
 -00000009done
 +0034shallow $(git rev-parse HEAD^)00000009done
  0000" | git upload-pack . > /dev/null 2> output.err &&
-       grep "waitpid (async) failed" output.err
+       # pack-objects survived
+       grep "Total.*, reused" output.err &&
+       # but there was an error, which must have been in rev-list
+       grep "bad tree object" output.err
  '
  
 +test_expect_success 'upload-pack fails due to error in pack-objects enumeration' '
 +
 +      ! echo "0032want $(git rev-parse HEAD)
 +00000009done
 +0000" | git upload-pack . > /dev/null 2> output.err &&
 +      grep "bad tree object" output.err &&
 +      grep "pack-objects died" output.err
 +'
 +
  test_expect_success 'create empty repository' '
  
        mkdir foo &&
diff --combined transport.c
index de0d5874a3d867d71eaec3cd1dde1bf2f09cfe4d,802ce7f233116cc52367b965e9e0d97bd8553535..8a42e76b3eafcb48b0904ab6f66b525624609477
@@@ -158,7 -158,7 +158,7 @@@ static struct ref *get_refs_via_rsync(s
  
        strbuf_addstr(&temp_dir, git_path("rsync-refs-XXXXXX"));
        if (!mkdtemp(temp_dir.buf))
 -              die ("Could not make temporary directory");
 +              die_errno ("Could not make temporary directory");
        temp_dir_len = temp_dir.len;
  
        strbuf_addstr(&buf, rsync_url(transport->url));
@@@ -321,7 -321,7 +321,7 @@@ static int rsync_transport_push(struct 
  
        strbuf_addstr(&temp_dir, git_path("rsync-refs-XXXXXX"));
        if (!mkdtemp(temp_dir.buf))
 -              die ("Could not make temporary directory");
 +              die_errno ("Could not make temporary directory");
        strbuf_addch(&temp_dir, '/');
  
        if (flags & TRANSPORT_PUSH_ALL) {
@@@ -396,7 -396,6 +396,6 @@@ static int curl_transport_push(struct t
  {
        const char **argv;
        int argc;
-       int err;
  
        if (flags & TRANSPORT_PUSH_MIRROR)
                return error("http transport does not support mirror mode");
        while (refspec_nr--)
                argv[argc++] = *refspec++;
        argv[argc] = NULL;
-       err = run_command_v_opt(argv, RUN_GIT_CMD);
-       switch (err) {
-       case -ERR_RUN_COMMAND_FORK:
-               error("unable to fork for %s", argv[0]);
-       case -ERR_RUN_COMMAND_EXEC:
-               error("unable to exec %s", argv[0]);
-               break;
-       case -ERR_RUN_COMMAND_WAITPID:
-       case -ERR_RUN_COMMAND_WAITPID_WRONG_PID:
-       case -ERR_RUN_COMMAND_WAITPID_SIGNAL:
-       case -ERR_RUN_COMMAND_WAITPID_NOEXIT:
-               error("%s died with strange error", argv[0]);
-       }
-       return !!err;
+       return !!run_command_v_opt(argv, RUN_GIT_CMD);
  }
  
  static struct ref *get_refs_via_curl(struct transport *transport, int for_push)
@@@ -719,30 -705,19 +705,30 @@@ static void update_tracking_ref(struct 
  
  #define SUMMARY_WIDTH (2 * DEFAULT_ABBREV + 3)
  
 -static void print_ref_status(char flag, const char *summary, struct ref *to, struct ref *from, const char *msg)
 -{
 -      fprintf(stderr, " %c %-*s ", flag, SUMMARY_WIDTH, summary);
 -      if (from)
 -              fprintf(stderr, "%s -> %s", prettify_refname(from->name), prettify_refname(to->name));
 -      else
 -              fputs(prettify_refname(to->name), stderr);
 -      if (msg) {
 -              fputs(" (", stderr);
 -              fputs(msg, stderr);
 -              fputc(')', stderr);
 +static void print_ref_status(char flag, const char *summary, struct ref *to, struct ref *from, const char *msg, int porcelain)
 +{
 +      if (porcelain) {
 +              if (from)
 +                      fprintf(stdout, "%c\t%s:%s\t", flag, from->name, to->name);
 +              else
 +                      fprintf(stdout, "%c\t:%s\t", flag, to->name);
 +              if (msg)
 +                      fprintf(stdout, "%s (%s)\n", summary, msg);
 +              else
 +                      fprintf(stdout, "%s\n", summary);
 +      } else {
 +              fprintf(stderr, " %c %-*s ", flag, SUMMARY_WIDTH, summary);
 +              if (from)
 +                      fprintf(stderr, "%s -> %s", prettify_refname(from->name), prettify_refname(to->name));
 +              else
 +                      fputs(prettify_refname(to->name), stderr);
 +              if (msg) {
 +                      fputs(" (", stderr);
 +                      fputs(msg, stderr);
 +                      fputc(')', stderr);
 +              }
 +              fputc('\n', stderr);
        }
 -      fputc('\n', stderr);
  }
  
  static const char *status_abbrev(unsigned char sha1[20])
        return find_unique_abbrev(sha1, DEFAULT_ABBREV);
  }
  
 -static void print_ok_ref_status(struct ref *ref)
 +static void print_ok_ref_status(struct ref *ref, int porcelain)
  {
        if (ref->deletion)
 -              print_ref_status('-', "[deleted]", ref, NULL, NULL);
 +              print_ref_status('-', "[deleted]", ref, NULL, NULL, porcelain);
        else if (is_null_sha1(ref->old_sha1))
                print_ref_status('*',
                        (!prefixcmp(ref->name, "refs/tags/") ? "[new tag]" :
 -                        "[new branch]"),
 -                      ref, ref->peer_ref, NULL);
 +                      "[new branch]"),
 +                      ref, ref->peer_ref, NULL, porcelain);
        else {
                char quickref[84];
                char type;
                }
                strcat(quickref, status_abbrev(ref->new_sha1));
  
 -              print_ref_status(type, quickref, ref, ref->peer_ref, msg);
 +              print_ref_status(type, quickref, ref, ref->peer_ref, msg, porcelain);
        }
  }
  
 -static int print_one_push_status(struct ref *ref, const char *dest, int count)
 +static int print_one_push_status(struct ref *ref, const char *dest, int count, int porcelain)
  {
        if (!count)
                fprintf(stderr, "To %s\n", dest);
  
        switch(ref->status) {
        case REF_STATUS_NONE:
 -              print_ref_status('X', "[no match]", ref, NULL, NULL);
 +              print_ref_status('X', "[no match]", ref, NULL, NULL, porcelain);
                break;
        case REF_STATUS_REJECT_NODELETE:
                print_ref_status('!', "[rejected]", ref, NULL,
 -                              "remote does not support deleting refs");
 +                                               "remote does not support deleting refs", porcelain);
                break;
        case REF_STATUS_UPTODATE:
                print_ref_status('=', "[up to date]", ref,
 -                              ref->peer_ref, NULL);
 +                                               ref->peer_ref, NULL, porcelain);
                break;
        case REF_STATUS_REJECT_NONFASTFORWARD:
                print_ref_status('!', "[rejected]", ref, ref->peer_ref,
 -                              "non-fast forward");
 +                                               "non-fast forward", porcelain);
                break;
        case REF_STATUS_REMOTE_REJECT:
                print_ref_status('!', "[remote rejected]", ref,
 -                              ref->deletion ? NULL : ref->peer_ref,
 -                              ref->remote_status);
 +                                               ref->deletion ? NULL : ref->peer_ref,
 +                                               ref->remote_status, porcelain);
                break;
        case REF_STATUS_EXPECTING_REPORT:
                print_ref_status('!', "[remote failure]", ref,
 -                              ref->deletion ? NULL : ref->peer_ref,
 -                              "remote failed to report status");
 +                                               ref->deletion ? NULL : ref->peer_ref,
 +                                               "remote failed to report status", porcelain);
                break;
        case REF_STATUS_OK:
 -              print_ok_ref_status(ref);
 +              print_ok_ref_status(ref, porcelain);
                break;
        }
  
        return 1;
  }
  
 -static void print_push_status(const char *dest, struct ref *refs, int verbose)
 +static void print_push_status(const char *dest, struct ref *refs,
 +                                                        int verbose, int porcelain)
  {
        struct ref *ref;
        int n = 0;
        if (verbose) {
                for (ref = refs; ref; ref = ref->next)
                        if (ref->status == REF_STATUS_UPTODATE)
 -                              n += print_one_push_status(ref, dest, n);
 +                              n += print_one_push_status(ref, dest, n, porcelain);
        }
  
        for (ref = refs; ref; ref = ref->next)
                if (ref->status == REF_STATUS_OK)
 -                      n += print_one_push_status(ref, dest, n);
 +                      n += print_one_push_status(ref, dest, n, porcelain);
  
        for (ref = refs; ref; ref = ref->next) {
                if (ref->status != REF_STATUS_NONE &&
                    ref->status != REF_STATUS_UPTODATE &&
                    ref->status != REF_STATUS_OK)
 -                      n += print_one_push_status(ref, dest, n);
 +                      n += print_one_push_status(ref, dest, n, porcelain);
        }
  }
  
@@@ -1009,7 -983,6 +995,7 @@@ int transport_push(struct transport *tr
                struct ref *local_refs = get_local_heads();
                int match_flags = MATCH_REFS_NONE;
                int verbose = flags & TRANSPORT_PUSH_VERBOSE;
 +              int porcelain = flags & TRANSPORT_PUSH_PORCELAIN;
                int ret;
  
                if (flags & TRANSPORT_PUSH_ALL)
  
                ret = transport->push_refs(transport, remote_refs, flags);
  
 -              print_push_status(transport->url, remote_refs, verbose);
 +              print_push_status(transport->url, remote_refs, verbose | porcelain, porcelain);
  
                if (!(flags & TRANSPORT_PUSH_DRY_RUN)) {
                        struct ref *ref;