builtin / receive-pack.con commit contrib: add credential helper for OS X Keychain (34961d3)
   1#include "builtin.h"
   2#include "pack.h"
   3#include "refs.h"
   4#include "pkt-line.h"
   5#include "sideband.h"
   6#include "run-command.h"
   7#include "exec_cmd.h"
   8#include "commit.h"
   9#include "object.h"
  10#include "remote.h"
  11#include "transport.h"
  12#include "string-list.h"
  13#include "sha1-array.h"
  14#include "connected.h"
  15
  16static const char receive_pack_usage[] = "git receive-pack <git-dir>";
  17
  18enum deny_action {
  19        DENY_UNCONFIGURED,
  20        DENY_IGNORE,
  21        DENY_WARN,
  22        DENY_REFUSE
  23};
  24
  25static int deny_deletes;
  26static int deny_non_fast_forwards;
  27static enum deny_action deny_current_branch = DENY_UNCONFIGURED;
  28static enum deny_action deny_delete_current = DENY_UNCONFIGURED;
  29static int receive_fsck_objects = -1;
  30static int transfer_fsck_objects = -1;
  31static int receive_unpack_limit = -1;
  32static int transfer_unpack_limit = -1;
  33static int unpack_limit = 100;
  34static int report_status;
  35static int use_sideband;
  36static int prefer_ofs_delta = 1;
  37static int auto_update_server_info;
  38static int auto_gc = 1;
  39static const char *head_name;
  40static int sent_capabilities;
  41
  42static enum deny_action parse_deny_action(const char *var, const char *value)
  43{
  44        if (value) {
  45                if (!strcasecmp(value, "ignore"))
  46                        return DENY_IGNORE;
  47                if (!strcasecmp(value, "warn"))
  48                        return DENY_WARN;
  49                if (!strcasecmp(value, "refuse"))
  50                        return DENY_REFUSE;
  51        }
  52        if (git_config_bool(var, value))
  53                return DENY_REFUSE;
  54        return DENY_IGNORE;
  55}
  56
  57static int receive_pack_config(const char *var, const char *value, void *cb)
  58{
  59        if (strcmp(var, "receive.denydeletes") == 0) {
  60                deny_deletes = git_config_bool(var, value);
  61                return 0;
  62        }
  63
  64        if (strcmp(var, "receive.denynonfastforwards") == 0) {
  65                deny_non_fast_forwards = git_config_bool(var, value);
  66                return 0;
  67        }
  68
  69        if (strcmp(var, "receive.unpacklimit") == 0) {
  70                receive_unpack_limit = git_config_int(var, value);
  71                return 0;
  72        }
  73
  74        if (strcmp(var, "transfer.unpacklimit") == 0) {
  75                transfer_unpack_limit = git_config_int(var, value);
  76                return 0;
  77        }
  78
  79        if (strcmp(var, "receive.fsckobjects") == 0) {
  80                receive_fsck_objects = git_config_bool(var, value);
  81                return 0;
  82        }
  83
  84        if (strcmp(var, "transfer.fsckobjects") == 0) {
  85                transfer_fsck_objects = git_config_bool(var, value);
  86                return 0;
  87        }
  88
  89        if (!strcmp(var, "receive.denycurrentbranch")) {
  90                deny_current_branch = parse_deny_action(var, value);
  91                return 0;
  92        }
  93
  94        if (strcmp(var, "receive.denydeletecurrent") == 0) {
  95                deny_delete_current = parse_deny_action(var, value);
  96                return 0;
  97        }
  98
  99        if (strcmp(var, "repack.usedeltabaseoffset") == 0) {
 100                prefer_ofs_delta = git_config_bool(var, value);
 101                return 0;
 102        }
 103
 104        if (strcmp(var, "receive.updateserverinfo") == 0) {
 105                auto_update_server_info = git_config_bool(var, value);
 106                return 0;
 107        }
 108
 109        if (strcmp(var, "receive.autogc") == 0) {
 110                auto_gc = git_config_bool(var, value);
 111                return 0;
 112        }
 113
 114        return git_default_config(var, value, cb);
 115}
 116
 117static int show_ref(const char *path, const unsigned char *sha1, int flag, void *cb_data)
 118{
 119        if (sent_capabilities)
 120                packet_write(1, "%s %s\n", sha1_to_hex(sha1), path);
 121        else
 122                packet_write(1, "%s %s%c%s%s\n",
 123                             sha1_to_hex(sha1), path, 0,
 124                             " report-status delete-refs side-band-64k",
 125                             prefer_ofs_delta ? " ofs-delta" : "");
 126        sent_capabilities = 1;
 127        return 0;
 128}
 129
 130static int show_ref_cb(const char *path, const unsigned char *sha1, int flag, void *cb_data)
 131{
 132        path = strip_namespace(path);
 133        /*
 134         * Advertise refs outside our current namespace as ".have"
 135         * refs, so that the client can use them to minimize data
 136         * transfer but will otherwise ignore them. This happens to
 137         * cover ".have" that are thrown in by add_one_alternate_ref()
 138         * to mark histories that are complete in our alternates as
 139         * well.
 140         */
 141        if (!path)
 142                path = ".have";
 143        return show_ref(path, sha1, flag, cb_data);
 144}
 145
 146static void write_head_info(void)
 147{
 148        for_each_ref(show_ref_cb, NULL);
 149        if (!sent_capabilities)
 150                show_ref("capabilities^{}", null_sha1, 0, NULL);
 151
 152}
 153
 154struct command {
 155        struct command *next;
 156        const char *error_string;
 157        unsigned int skip_update:1,
 158                     did_not_exist:1;
 159        unsigned char old_sha1[20];
 160        unsigned char new_sha1[20];
 161        char ref_name[FLEX_ARRAY]; /* more */
 162};
 163
 164static const char pre_receive_hook[] = "hooks/pre-receive";
 165static const char post_receive_hook[] = "hooks/post-receive";
 166
 167static void rp_error(const char *err, ...) __attribute__((format (printf, 1, 2)));
 168static void rp_warning(const char *err, ...) __attribute__((format (printf, 1, 2)));
 169
 170static void report_message(const char *prefix, const char *err, va_list params)
 171{
 172        int sz = strlen(prefix);
 173        char msg[4096];
 174
 175        strncpy(msg, prefix, sz);
 176        sz += vsnprintf(msg + sz, sizeof(msg) - sz, err, params);
 177        if (sz > (sizeof(msg) - 1))
 178                sz = sizeof(msg) - 1;
 179        msg[sz++] = '\n';
 180
 181        if (use_sideband)
 182                send_sideband(1, 2, msg, sz, use_sideband);
 183        else
 184                xwrite(2, msg, sz);
 185}
 186
 187static void rp_warning(const char *err, ...)
 188{
 189        va_list params;
 190        va_start(params, err);
 191        report_message("warning: ", err, params);
 192        va_end(params);
 193}
 194
 195static void rp_error(const char *err, ...)
 196{
 197        va_list params;
 198        va_start(params, err);
 199        report_message("error: ", err, params);
 200        va_end(params);
 201}
 202
 203static int copy_to_sideband(int in, int out, void *arg)
 204{
 205        char data[128];
 206        while (1) {
 207                ssize_t sz = xread(in, data, sizeof(data));
 208                if (sz <= 0)
 209                        break;
 210                send_sideband(1, 2, data, sz, use_sideband);
 211        }
 212        close(in);
 213        return 0;
 214}
 215
 216typedef int (*feed_fn)(void *, const char **, size_t *);
 217static int run_and_feed_hook(const char *hook_name, feed_fn feed, void *feed_state)
 218{
 219        struct child_process proc;
 220        struct async muxer;
 221        const char *argv[2];
 222        int code;
 223
 224        if (access(hook_name, X_OK) < 0)
 225                return 0;
 226
 227        argv[0] = hook_name;
 228        argv[1] = NULL;
 229
 230        memset(&proc, 0, sizeof(proc));
 231        proc.argv = argv;
 232        proc.in = -1;
 233        proc.stdout_to_stderr = 1;
 234
 235        if (use_sideband) {
 236                memset(&muxer, 0, sizeof(muxer));
 237                muxer.proc = copy_to_sideband;
 238                muxer.in = -1;
 239                code = start_async(&muxer);
 240                if (code)
 241                        return code;
 242                proc.err = muxer.in;
 243        }
 244
 245        code = start_command(&proc);
 246        if (code) {
 247                if (use_sideband)
 248                        finish_async(&muxer);
 249                return code;
 250        }
 251
 252        while (1) {
 253                const char *buf;
 254                size_t n;
 255                if (feed(feed_state, &buf, &n))
 256                        break;
 257                if (write_in_full(proc.in, buf, n) != n)
 258                        break;
 259        }
 260        close(proc.in);
 261        if (use_sideband)
 262                finish_async(&muxer);
 263        return finish_command(&proc);
 264}
 265
 266struct receive_hook_feed_state {
 267        struct command *cmd;
 268        int skip_broken;
 269        struct strbuf buf;
 270};
 271
 272static int feed_receive_hook(void *state_, const char **bufp, size_t *sizep)
 273{
 274        struct receive_hook_feed_state *state = state_;
 275        struct command *cmd = state->cmd;
 276
 277        while (cmd &&
 278               state->skip_broken && (cmd->error_string || cmd->did_not_exist))
 279                cmd = cmd->next;
 280        if (!cmd)
 281                return -1; /* EOF */
 282        strbuf_reset(&state->buf);
 283        strbuf_addf(&state->buf, "%s %s %s\n",
 284                    sha1_to_hex(cmd->old_sha1), sha1_to_hex(cmd->new_sha1),
 285                    cmd->ref_name);
 286        state->cmd = cmd->next;
 287        if (bufp) {
 288                *bufp = state->buf.buf;
 289                *sizep = state->buf.len;
 290        }
 291        return 0;
 292}
 293
 294static int run_receive_hook(struct command *commands, const char *hook_name,
 295                            int skip_broken)
 296{
 297        struct receive_hook_feed_state state;
 298        int status;
 299
 300        strbuf_init(&state.buf, 0);
 301        state.cmd = commands;
 302        state.skip_broken = skip_broken;
 303        if (feed_receive_hook(&state, NULL, NULL))
 304                return 0;
 305        state.cmd = commands;
 306        status = run_and_feed_hook(hook_name, feed_receive_hook, &state);
 307        strbuf_release(&state.buf);
 308        return status;
 309}
 310
 311static int run_update_hook(struct command *cmd)
 312{
 313        static const char update_hook[] = "hooks/update";
 314        const char *argv[5];
 315        struct child_process proc;
 316        int code;
 317
 318        if (access(update_hook, X_OK) < 0)
 319                return 0;
 320
 321        argv[0] = update_hook;
 322        argv[1] = cmd->ref_name;
 323        argv[2] = sha1_to_hex(cmd->old_sha1);
 324        argv[3] = sha1_to_hex(cmd->new_sha1);
 325        argv[4] = NULL;
 326
 327        memset(&proc, 0, sizeof(proc));
 328        proc.no_stdin = 1;
 329        proc.stdout_to_stderr = 1;
 330        proc.err = use_sideband ? -1 : 0;
 331        proc.argv = argv;
 332
 333        code = start_command(&proc);
 334        if (code)
 335                return code;
 336        if (use_sideband)
 337                copy_to_sideband(proc.err, -1, NULL);
 338        return finish_command(&proc);
 339}
 340
 341static int is_ref_checked_out(const char *ref)
 342{
 343        if (is_bare_repository())
 344                return 0;
 345
 346        if (!head_name)
 347                return 0;
 348        return !strcmp(head_name, ref);
 349}
 350
 351static char *refuse_unconfigured_deny_msg[] = {
 352        "By default, updating the current branch in a non-bare repository",
 353        "is denied, because it will make the index and work tree inconsistent",
 354        "with what you pushed, and will require 'git reset --hard' to match",
 355        "the work tree to HEAD.",
 356        "",
 357        "You can set 'receive.denyCurrentBranch' configuration variable to",
 358        "'ignore' or 'warn' in the remote repository to allow pushing into",
 359        "its current branch; however, this is not recommended unless you",
 360        "arranged to update its work tree to match what you pushed in some",
 361        "other way.",
 362        "",
 363        "To squelch this message and still keep the default behaviour, set",
 364        "'receive.denyCurrentBranch' configuration variable to 'refuse'."
 365};
 366
 367static void refuse_unconfigured_deny(void)
 368{
 369        int i;
 370        for (i = 0; i < ARRAY_SIZE(refuse_unconfigured_deny_msg); i++)
 371                rp_error("%s", refuse_unconfigured_deny_msg[i]);
 372}
 373
 374static char *refuse_unconfigured_deny_delete_current_msg[] = {
 375        "By default, deleting the current branch is denied, because the next",
 376        "'git clone' won't result in any file checked out, causing confusion.",
 377        "",
 378        "You can set 'receive.denyDeleteCurrent' configuration variable to",
 379        "'warn' or 'ignore' in the remote repository to allow deleting the",
 380        "current branch, with or without a warning message.",
 381        "",
 382        "To squelch this message, you can set it to 'refuse'."
 383};
 384
 385static void refuse_unconfigured_deny_delete_current(void)
 386{
 387        int i;
 388        for (i = 0;
 389             i < ARRAY_SIZE(refuse_unconfigured_deny_delete_current_msg);
 390             i++)
 391                rp_error("%s", refuse_unconfigured_deny_delete_current_msg[i]);
 392}
 393
 394static const char *update(struct command *cmd)
 395{
 396        const char *name = cmd->ref_name;
 397        struct strbuf namespaced_name_buf = STRBUF_INIT;
 398        const char *namespaced_name;
 399        unsigned char *old_sha1 = cmd->old_sha1;
 400        unsigned char *new_sha1 = cmd->new_sha1;
 401        struct ref_lock *lock;
 402
 403        /* only refs/... are allowed */
 404        if (prefixcmp(name, "refs/") || check_refname_format(name + 5, 0)) {
 405                rp_error("refusing to create funny ref '%s' remotely", name);
 406                return "funny refname";
 407        }
 408
 409        strbuf_addf(&namespaced_name_buf, "%s%s", get_git_namespace(), name);
 410        namespaced_name = strbuf_detach(&namespaced_name_buf, NULL);
 411
 412        if (is_ref_checked_out(namespaced_name)) {
 413                switch (deny_current_branch) {
 414                case DENY_IGNORE:
 415                        break;
 416                case DENY_WARN:
 417                        rp_warning("updating the current branch");
 418                        break;
 419                case DENY_REFUSE:
 420                case DENY_UNCONFIGURED:
 421                        rp_error("refusing to update checked out branch: %s", name);
 422                        if (deny_current_branch == DENY_UNCONFIGURED)
 423                                refuse_unconfigured_deny();
 424                        return "branch is currently checked out";
 425                }
 426        }
 427
 428        if (!is_null_sha1(new_sha1) && !has_sha1_file(new_sha1)) {
 429                error("unpack should have generated %s, "
 430                      "but I can't find it!", sha1_to_hex(new_sha1));
 431                return "bad pack";
 432        }
 433
 434        if (!is_null_sha1(old_sha1) && is_null_sha1(new_sha1)) {
 435                if (deny_deletes && !prefixcmp(name, "refs/heads/")) {
 436                        rp_error("denying ref deletion for %s", name);
 437                        return "deletion prohibited";
 438                }
 439
 440                if (!strcmp(namespaced_name, head_name)) {
 441                        switch (deny_delete_current) {
 442                        case DENY_IGNORE:
 443                                break;
 444                        case DENY_WARN:
 445                                rp_warning("deleting the current branch");
 446                                break;
 447                        case DENY_REFUSE:
 448                        case DENY_UNCONFIGURED:
 449                                if (deny_delete_current == DENY_UNCONFIGURED)
 450                                        refuse_unconfigured_deny_delete_current();
 451                                rp_error("refusing to delete the current branch: %s", name);
 452                                return "deletion of the current branch prohibited";
 453                        }
 454                }
 455        }
 456
 457        if (deny_non_fast_forwards && !is_null_sha1(new_sha1) &&
 458            !is_null_sha1(old_sha1) &&
 459            !prefixcmp(name, "refs/heads/")) {
 460                struct object *old_object, *new_object;
 461                struct commit *old_commit, *new_commit;
 462                struct commit_list *bases, *ent;
 463
 464                old_object = parse_object(old_sha1);
 465                new_object = parse_object(new_sha1);
 466
 467                if (!old_object || !new_object ||
 468                    old_object->type != OBJ_COMMIT ||
 469                    new_object->type != OBJ_COMMIT) {
 470                        error("bad sha1 objects for %s", name);
 471                        return "bad ref";
 472                }
 473                old_commit = (struct commit *)old_object;
 474                new_commit = (struct commit *)new_object;
 475                bases = get_merge_bases(old_commit, new_commit, 1);
 476                for (ent = bases; ent; ent = ent->next)
 477                        if (!hashcmp(old_sha1, ent->item->object.sha1))
 478                                break;
 479                free_commit_list(bases);
 480                if (!ent) {
 481                        rp_error("denying non-fast-forward %s"
 482                                 " (you should pull first)", name);
 483                        return "non-fast-forward";
 484                }
 485        }
 486        if (run_update_hook(cmd)) {
 487                rp_error("hook declined to update %s", name);
 488                return "hook declined";
 489        }
 490
 491        if (is_null_sha1(new_sha1)) {
 492                if (!parse_object(old_sha1)) {
 493                        old_sha1 = NULL;
 494                        if (ref_exists(name)) {
 495                                rp_warning("Allowing deletion of corrupt ref.");
 496                        } else {
 497                                rp_warning("Deleting a non-existent ref.");
 498                                cmd->did_not_exist = 1;
 499                        }
 500                }
 501                if (delete_ref(namespaced_name, old_sha1, 0)) {
 502                        rp_error("failed to delete %s", name);
 503                        return "failed to delete";
 504                }
 505                return NULL; /* good */
 506        }
 507        else {
 508                lock = lock_any_ref_for_update(namespaced_name, old_sha1, 0);
 509                if (!lock) {
 510                        rp_error("failed to lock %s", name);
 511                        return "failed to lock";
 512                }
 513                if (write_ref_sha1(lock, new_sha1, "push")) {
 514                        return "failed to write"; /* error() already called */
 515                }
 516                return NULL; /* good */
 517        }
 518}
 519
 520static char update_post_hook[] = "hooks/post-update";
 521
 522static void run_update_post_hook(struct command *commands)
 523{
 524        struct command *cmd;
 525        int argc;
 526        const char **argv;
 527        struct child_process proc;
 528
 529        for (argc = 0, cmd = commands; cmd; cmd = cmd->next) {
 530                if (cmd->error_string || cmd->did_not_exist)
 531                        continue;
 532                argc++;
 533        }
 534        if (!argc || access(update_post_hook, X_OK) < 0)
 535                return;
 536        argv = xmalloc(sizeof(*argv) * (2 + argc));
 537        argv[0] = update_post_hook;
 538
 539        for (argc = 1, cmd = commands; cmd; cmd = cmd->next) {
 540                char *p;
 541                if (cmd->error_string || cmd->did_not_exist)
 542                        continue;
 543                p = xmalloc(strlen(cmd->ref_name) + 1);
 544                strcpy(p, cmd->ref_name);
 545                argv[argc] = p;
 546                argc++;
 547        }
 548        argv[argc] = NULL;
 549
 550        memset(&proc, 0, sizeof(proc));
 551        proc.no_stdin = 1;
 552        proc.stdout_to_stderr = 1;
 553        proc.err = use_sideband ? -1 : 0;
 554        proc.argv = argv;
 555
 556        if (!start_command(&proc)) {
 557                if (use_sideband)
 558                        copy_to_sideband(proc.err, -1, NULL);
 559                finish_command(&proc);
 560        }
 561}
 562
 563static void check_aliased_update(struct command *cmd, struct string_list *list)
 564{
 565        struct strbuf buf = STRBUF_INIT;
 566        const char *dst_name;
 567        struct string_list_item *item;
 568        struct command *dst_cmd;
 569        unsigned char sha1[20];
 570        char cmd_oldh[41], cmd_newh[41], dst_oldh[41], dst_newh[41];
 571        int flag;
 572
 573        strbuf_addf(&buf, "%s%s", get_git_namespace(), cmd->ref_name);
 574        dst_name = resolve_ref(buf.buf, sha1, 0, &flag);
 575        strbuf_release(&buf);
 576
 577        if (!(flag & REF_ISSYMREF))
 578                return;
 579
 580        dst_name = strip_namespace(dst_name);
 581        if (!dst_name) {
 582                rp_error("refusing update to broken symref '%s'", cmd->ref_name);
 583                cmd->skip_update = 1;
 584                cmd->error_string = "broken symref";
 585                return;
 586        }
 587
 588        if ((item = string_list_lookup(list, dst_name)) == NULL)
 589                return;
 590
 591        cmd->skip_update = 1;
 592
 593        dst_cmd = (struct command *) item->util;
 594
 595        if (!hashcmp(cmd->old_sha1, dst_cmd->old_sha1) &&
 596            !hashcmp(cmd->new_sha1, dst_cmd->new_sha1))
 597                return;
 598
 599        dst_cmd->skip_update = 1;
 600
 601        strcpy(cmd_oldh, find_unique_abbrev(cmd->old_sha1, DEFAULT_ABBREV));
 602        strcpy(cmd_newh, find_unique_abbrev(cmd->new_sha1, DEFAULT_ABBREV));
 603        strcpy(dst_oldh, find_unique_abbrev(dst_cmd->old_sha1, DEFAULT_ABBREV));
 604        strcpy(dst_newh, find_unique_abbrev(dst_cmd->new_sha1, DEFAULT_ABBREV));
 605        rp_error("refusing inconsistent update between symref '%s' (%s..%s) and"
 606                 " its target '%s' (%s..%s)",
 607                 cmd->ref_name, cmd_oldh, cmd_newh,
 608                 dst_cmd->ref_name, dst_oldh, dst_newh);
 609
 610        cmd->error_string = dst_cmd->error_string =
 611                "inconsistent aliased update";
 612}
 613
 614static void check_aliased_updates(struct command *commands)
 615{
 616        struct command *cmd;
 617        struct string_list ref_list = STRING_LIST_INIT_NODUP;
 618
 619        for (cmd = commands; cmd; cmd = cmd->next) {
 620                struct string_list_item *item =
 621                        string_list_append(&ref_list, cmd->ref_name);
 622                item->util = (void *)cmd;
 623        }
 624        sort_string_list(&ref_list);
 625
 626        for (cmd = commands; cmd; cmd = cmd->next)
 627                check_aliased_update(cmd, &ref_list);
 628
 629        string_list_clear(&ref_list, 0);
 630}
 631
 632static int command_singleton_iterator(void *cb_data, unsigned char sha1[20])
 633{
 634        struct command **cmd_list = cb_data;
 635        struct command *cmd = *cmd_list;
 636
 637        if (!cmd || is_null_sha1(cmd->new_sha1))
 638                return -1; /* end of list */
 639        *cmd_list = NULL; /* this returns only one */
 640        hashcpy(sha1, cmd->new_sha1);
 641        return 0;
 642}
 643
 644static void set_connectivity_errors(struct command *commands)
 645{
 646        struct command *cmd;
 647
 648        for (cmd = commands; cmd; cmd = cmd->next) {
 649                struct command *singleton = cmd;
 650                if (!check_everything_connected(command_singleton_iterator,
 651                                                0, &singleton))
 652                        continue;
 653                cmd->error_string = "missing necessary objects";
 654        }
 655}
 656
 657static int iterate_receive_command_list(void *cb_data, unsigned char sha1[20])
 658{
 659        struct command **cmd_list = cb_data;
 660        struct command *cmd = *cmd_list;
 661
 662        while (cmd) {
 663                if (!is_null_sha1(cmd->new_sha1)) {
 664                        hashcpy(sha1, cmd->new_sha1);
 665                        *cmd_list = cmd->next;
 666                        return 0;
 667                }
 668                cmd = cmd->next;
 669        }
 670        *cmd_list = NULL;
 671        return -1; /* end of list */
 672}
 673
 674static void execute_commands(struct command *commands, const char *unpacker_error)
 675{
 676        struct command *cmd;
 677        unsigned char sha1[20];
 678
 679        if (unpacker_error) {
 680                for (cmd = commands; cmd; cmd = cmd->next)
 681                        cmd->error_string = "n/a (unpacker error)";
 682                return;
 683        }
 684
 685        cmd = commands;
 686        if (check_everything_connected(iterate_receive_command_list,
 687                                       0, &cmd))
 688                set_connectivity_errors(commands);
 689
 690        if (run_receive_hook(commands, pre_receive_hook, 0)) {
 691                for (cmd = commands; cmd; cmd = cmd->next)
 692                        cmd->error_string = "pre-receive hook declined";
 693                return;
 694        }
 695
 696        check_aliased_updates(commands);
 697
 698        head_name = resolve_ref("HEAD", sha1, 0, NULL);
 699
 700        for (cmd = commands; cmd; cmd = cmd->next)
 701                if (!cmd->skip_update)
 702                        cmd->error_string = update(cmd);
 703}
 704
 705static struct command *read_head_info(void)
 706{
 707        struct command *commands = NULL;
 708        struct command **p = &commands;
 709        for (;;) {
 710                static char line[1000];
 711                unsigned char old_sha1[20], new_sha1[20];
 712                struct command *cmd;
 713                char *refname;
 714                int len, reflen;
 715
 716                len = packet_read_line(0, line, sizeof(line));
 717                if (!len)
 718                        break;
 719                if (line[len-1] == '\n')
 720                        line[--len] = 0;
 721                if (len < 83 ||
 722                    line[40] != ' ' ||
 723                    line[81] != ' ' ||
 724                    get_sha1_hex(line, old_sha1) ||
 725                    get_sha1_hex(line + 41, new_sha1))
 726                        die("protocol error: expected old/new/ref, got '%s'",
 727                            line);
 728
 729                refname = line + 82;
 730                reflen = strlen(refname);
 731                if (reflen + 82 < len) {
 732                        if (strstr(refname + reflen + 1, "report-status"))
 733                                report_status = 1;
 734                        if (strstr(refname + reflen + 1, "side-band-64k"))
 735                                use_sideband = LARGE_PACKET_MAX;
 736                }
 737                cmd = xcalloc(1, sizeof(struct command) + len - 80);
 738                hashcpy(cmd->old_sha1, old_sha1);
 739                hashcpy(cmd->new_sha1, new_sha1);
 740                memcpy(cmd->ref_name, line + 82, len - 81);
 741                *p = cmd;
 742                p = &cmd->next;
 743        }
 744        return commands;
 745}
 746
 747static const char *parse_pack_header(struct pack_header *hdr)
 748{
 749        switch (read_pack_header(0, hdr)) {
 750        case PH_ERROR_EOF:
 751                return "eof before pack header was fully read";
 752
 753        case PH_ERROR_PACK_SIGNATURE:
 754                return "protocol error (pack signature mismatch detected)";
 755
 756        case PH_ERROR_PROTOCOL:
 757                return "protocol error (pack version unsupported)";
 758
 759        default:
 760                return "unknown error in parse_pack_header";
 761
 762        case 0:
 763                return NULL;
 764        }
 765}
 766
 767static const char *pack_lockfile;
 768
 769static const char *unpack(void)
 770{
 771        struct pack_header hdr;
 772        const char *hdr_err;
 773        char hdr_arg[38];
 774        int fsck_objects = (receive_fsck_objects >= 0
 775                            ? receive_fsck_objects
 776                            : transfer_fsck_objects >= 0
 777                            ? transfer_fsck_objects
 778                            : 0);
 779
 780        hdr_err = parse_pack_header(&hdr);
 781        if (hdr_err)
 782                return hdr_err;
 783        snprintf(hdr_arg, sizeof(hdr_arg),
 784                        "--pack_header=%"PRIu32",%"PRIu32,
 785                        ntohl(hdr.hdr_version), ntohl(hdr.hdr_entries));
 786
 787        if (ntohl(hdr.hdr_entries) < unpack_limit) {
 788                int code, i = 0;
 789                const char *unpacker[4];
 790                unpacker[i++] = "unpack-objects";
 791                if (fsck_objects)
 792                        unpacker[i++] = "--strict";
 793                unpacker[i++] = hdr_arg;
 794                unpacker[i++] = NULL;
 795                code = run_command_v_opt(unpacker, RUN_GIT_CMD);
 796                if (!code)
 797                        return NULL;
 798                return "unpack-objects abnormal exit";
 799        } else {
 800                const char *keeper[7];
 801                int s, status, i = 0;
 802                char keep_arg[256];
 803                struct child_process ip;
 804
 805                s = sprintf(keep_arg, "--keep=receive-pack %"PRIuMAX" on ", (uintmax_t) getpid());
 806                if (gethostname(keep_arg + s, sizeof(keep_arg) - s))
 807                        strcpy(keep_arg + s, "localhost");
 808
 809                keeper[i++] = "index-pack";
 810                keeper[i++] = "--stdin";
 811                if (fsck_objects)
 812                        keeper[i++] = "--strict";
 813                keeper[i++] = "--fix-thin";
 814                keeper[i++] = hdr_arg;
 815                keeper[i++] = keep_arg;
 816                keeper[i++] = NULL;
 817                memset(&ip, 0, sizeof(ip));
 818                ip.argv = keeper;
 819                ip.out = -1;
 820                ip.git_cmd = 1;
 821                status = start_command(&ip);
 822                if (status) {
 823                        return "index-pack fork failed";
 824                }
 825                pack_lockfile = index_pack_lockfile(ip.out);
 826                close(ip.out);
 827                status = finish_command(&ip);
 828                if (!status) {
 829                        reprepare_packed_git();
 830                        return NULL;
 831                }
 832                return "index-pack abnormal exit";
 833        }
 834}
 835
 836static void report(struct command *commands, const char *unpack_status)
 837{
 838        struct command *cmd;
 839        struct strbuf buf = STRBUF_INIT;
 840
 841        packet_buf_write(&buf, "unpack %s\n",
 842                         unpack_status ? unpack_status : "ok");
 843        for (cmd = commands; cmd; cmd = cmd->next) {
 844                if (!cmd->error_string)
 845                        packet_buf_write(&buf, "ok %s\n",
 846                                         cmd->ref_name);
 847                else
 848                        packet_buf_write(&buf, "ng %s %s\n",
 849                                         cmd->ref_name, cmd->error_string);
 850        }
 851        packet_buf_flush(&buf);
 852
 853        if (use_sideband)
 854                send_sideband(1, 1, buf.buf, buf.len, use_sideband);
 855        else
 856                safe_write(1, buf.buf, buf.len);
 857        strbuf_release(&buf);
 858}
 859
 860static int delete_only(struct command *commands)
 861{
 862        struct command *cmd;
 863        for (cmd = commands; cmd; cmd = cmd->next) {
 864                if (!is_null_sha1(cmd->new_sha1))
 865                        return 0;
 866        }
 867        return 1;
 868}
 869
 870static void add_one_alternate_sha1(const unsigned char sha1[20], void *unused)
 871{
 872        add_extra_ref(".have", sha1, 0);
 873}
 874
 875static void collect_one_alternate_ref(const struct ref *ref, void *data)
 876{
 877        struct sha1_array *sa = data;
 878        sha1_array_append(sa, ref->old_sha1);
 879}
 880
 881static void add_alternate_refs(void)
 882{
 883        struct sha1_array sa = SHA1_ARRAY_INIT;
 884        for_each_alternate_ref(collect_one_alternate_ref, &sa);
 885        sha1_array_for_each_unique(&sa, add_one_alternate_sha1, NULL);
 886        sha1_array_clear(&sa);
 887}
 888
 889int cmd_receive_pack(int argc, const char **argv, const char *prefix)
 890{
 891        int advertise_refs = 0;
 892        int stateless_rpc = 0;
 893        int i;
 894        char *dir = NULL;
 895        struct command *commands;
 896
 897        packet_trace_identity("receive-pack");
 898
 899        argv++;
 900        for (i = 1; i < argc; i++) {
 901                const char *arg = *argv++;
 902
 903                if (*arg == '-') {
 904                        if (!strcmp(arg, "--advertise-refs")) {
 905                                advertise_refs = 1;
 906                                continue;
 907                        }
 908                        if (!strcmp(arg, "--stateless-rpc")) {
 909                                stateless_rpc = 1;
 910                                continue;
 911                        }
 912
 913                        usage(receive_pack_usage);
 914                }
 915                if (dir)
 916                        usage(receive_pack_usage);
 917                dir = xstrdup(arg);
 918        }
 919        if (!dir)
 920                usage(receive_pack_usage);
 921
 922        setup_path();
 923
 924        if (!enter_repo(dir, 0))
 925                die("'%s' does not appear to be a git repository", dir);
 926
 927        if (is_repository_shallow())
 928                die("attempt to push into a shallow repository");
 929
 930        git_config(receive_pack_config, NULL);
 931
 932        if (0 <= transfer_unpack_limit)
 933                unpack_limit = transfer_unpack_limit;
 934        else if (0 <= receive_unpack_limit)
 935                unpack_limit = receive_unpack_limit;
 936
 937        if (advertise_refs || !stateless_rpc) {
 938                add_alternate_refs();
 939                write_head_info();
 940                clear_extra_refs();
 941
 942                /* EOF */
 943                packet_flush(1);
 944        }
 945        if (advertise_refs)
 946                return 0;
 947
 948        if ((commands = read_head_info()) != NULL) {
 949                const char *unpack_status = NULL;
 950
 951                if (!delete_only(commands))
 952                        unpack_status = unpack();
 953                execute_commands(commands, unpack_status);
 954                if (pack_lockfile)
 955                        unlink_or_warn(pack_lockfile);
 956                if (report_status)
 957                        report(commands, unpack_status);
 958                run_receive_hook(commands, post_receive_hook, 1);
 959                run_update_post_hook(commands);
 960                if (auto_gc) {
 961                        const char *argv_gc_auto[] = {
 962                                "gc", "--auto", "--quiet", NULL,
 963                        };
 964                        run_command_v_opt(argv_gc_auto, RUN_GIT_CMD);
 965                }
 966                if (auto_update_server_info)
 967                        update_server_info(0);
 968        }
 969        if (use_sideband)
 970                packet_flush(1);
 971        return 0;
 972}