chiark / gitweb /
test suite: Always pass LC_COLLATE=C to sort(1).
[dgit.git] / dgit
diff --git a/dgit b/dgit
index 88db243261790717921deba420dea1ff3ff390cc..ca5737533847ee3d4d821fcf6eff7d2967e9b7bd 100755 (executable)
--- a/dgit
+++ b/dgit
@@ -1975,12 +1975,12 @@ END
            if ($found_same) {
                # in archive, delete from .changes if it's there
                $changed{$file} = "removed" if
-                   $changes->{$fname} =~ s/^.* \Q$file\E$(?:)\n//m;
-           } elsif ($changes->{$fname} =~ m/^.* \Q$file\E$(?:)\n/m) {
+                   $changes->{$fname} =~ s/\n.* \Q$file\E$(?:)$//m;
+           } elsif ($changes->{$fname} =~ m/^.* \Q$file\E$(?:)$/m) {
                # not in archive, but it's here in the .changes
            } else {
                my $dsc_data = getfield $dsc, $fname;
-               $dsc_data =~ m/^(.* \Q$file\E$)\n/m or die "$dsc_data $file ?";
+               $dsc_data =~ m/^(.* \Q$file\E$)$/m or die "$dsc_data $file ?";
                my $extra = $1;
                $extra =~ s/ \d+ /$&$placementinfo /
                    or die "$fname $extra >$dsc_data< ?"
@@ -2851,15 +2851,14 @@ sub mergeinfo_version ($) {
 
 sub fetch_from_archive_record_1 ($) {
     my ($hash) = @_;
-    runcmd @git, qw(update-ref -m), "dgit fetch $csuite",
-           'DGIT_ARCHIVE', $hash;
+    runcmd git_update_ref_cmd "dgit fetch $csuite", 'DGIT_ARCHIVE', $hash;
     cmdoutput @git, qw(log -n2), $hash;
     # ... gives git a chance to complain if our commit is malformed
 }
 
 sub fetch_from_archive_record_2 ($) {
     my ($hash) = @_;
-    my @upd_cmd = (@git, qw(update-ref -m), 'dgit fetch', lrref(), $hash);
+    my @upd_cmd = (git_update_ref_cmd 'dgit fetch', lrref(), $hash);
     if (act_local()) {
        cmdoutput @upd_cmd;
     } else {
@@ -3558,7 +3557,7 @@ sub fork_for_multisuite ($) {
        my $csubsuite = multisuite_suite_child($tsuite, \@mergeinputs,
                                               sub {
             @end = ();
-            fetch();
+            fetch_one();
            finish 0;
        });
        # xxx collecte the ref here
@@ -3716,7 +3715,7 @@ sub clone ($) {
     clone_finish($dstdir);
 }
 
-sub fetch () {
+sub fetch_one () {
     canonicalise_suite();
     if (check_for_git()) {
        git_fetch_us();
@@ -3739,10 +3738,14 @@ END
     printdone "fetched into ".lrref();
 }
 
-sub pull () {
+sub dofetch () {
     my $multi_fetched = fork_for_multisuite(sub { });
-    fetch() unless $multi_fetched; # parent
-    return if $multi_fetched eq '0'; # child
+    fetch_one() unless $multi_fetched; # parent
+    finish 0 if $multi_fetched eq '0'; # child
+}
+
+sub pull () {
+    dofetch();
     runcmd_ordryrun_local @git, qw(merge -m),"Merge from $csuite [dgit]",
         lrref();
     printdone "fetched to ".lrref()." and merged into HEAD";
@@ -3850,7 +3853,7 @@ sub maybe_split_brain_save ($$$) {
     # => message fragment "$saved" describing disposition of $dgitview
     return "commit id $dgitview" unless defined $split_brain_save;
     my @cmd = (shell_cmd 'cd "$1"; shift', $maindir,
-              @git, qw(update-ref -m),
+              git_update_ref_cmd
               "dgit --dgit-view-save $msg HEAD=$headref",
               $split_brain_save, $dgitview);
     runcmd @cmd;
@@ -4014,10 +4017,12 @@ sub splitbrain_pseudomerge ($$$$) {
        infopair_cond_ff($i_dep14, [ $maintview, 'HEAD' ]);
        1;
     }) {
+        $@ =~ s/^\n//; chomp $@;
        print STDERR <<END;
-$us: check failed (maybe --overwrite is needed, consult documentation)
+$@
+| Not fast forward; maybe --overwrite is needed, see dgit(1)
 END
-       die "$@";
+       finish -1;
     }
 
     my $r = pseudomerge_make_commit
@@ -4050,7 +4055,7 @@ sub plain_overwrite_pseudomerge ($$$) {
        $clogp, $head, $archive_hash, $i_arch_v,
        "dgit", $m;
 
-    runcmd @git, qw(update-ref -m), $m, 'HEAD', $r, $head;
+    runcmd git_update_ref_cmd $m, 'HEAD', $r, $head;
 
     progress "Make pseudo-merge of $i_arch_v->[0] into your HEAD.";
     return $r;
@@ -4496,7 +4501,7 @@ END
 
     runcmd_ordryrun @git,
        qw(-c push.followTags=false push), access_giturl(), @pushrefs;
-    runcmd_ordryrun @git, qw(update-ref -m), 'dgit push', lrref(), $dgithead;
+    runcmd_ordryrun git_update_ref_cmd 'dgit push', lrref(), $dgithead;
 
     supplementary_message(<<'END');
 Push failed, while obtaining signatures on the .changes and .dsc.
@@ -4596,11 +4601,15 @@ sub branchsuite () {
     }
 }
 
-sub fetchpullargs () {
+sub package_from_d_control () {
     if (!defined $package) {
        my $sourcep = parsecontrol('debian/control','debian/control');
        $package = getfield $sourcep, 'Source';
     }
+}
+
+sub fetchpullargs () {
+    package_from_d_control();
     if (@ARGV==0) {
        $isuite = branchsuite();
        if (!$isuite) {
@@ -4619,9 +4628,7 @@ sub fetchpullargs () {
 sub cmd_fetch {
     parseopts();
     fetchpullargs();
-    my $multi_fetched = fork_for_multisuite(sub { });
-    finish 0 if $multi_fetched;
-    fetch();
+    dofetch();
 }
 
 sub cmd_pull {
@@ -4636,6 +4643,40 @@ END
     pull();
 }
 
+sub cmd_checkout {
+    parseopts();
+    package_from_d_control();
+    @ARGV==1 or badusage "dgit checkout needs a suite argument";
+    ($isuite) = @ARGV;
+    notpushing();
+
+    foreach my $canon (qw(0 1)) {
+       if (!$canon) {
+           $csuite= $isuite;
+       } else {
+           undef $csuite;
+           canonicalise_suite();
+       }
+       if (length git_get_ref lref()) {
+           # local branch already exists, yay
+           last;
+       }
+       if (!length git_get_ref lrref()) {
+           if (!$canon) {
+               # nope
+               next;
+           }
+           dofetch();
+       }
+       # now lrref exists
+       runcmd (@git, qw(update-ref), lref(), lrref(), '');
+       last;
+    }
+    local $ENV{GIT_REFLOG_ACTION} = git_reflog_action_msg
+        "dgit checkout $isuite";
+    runcmd (@git, qw(checkout), lref());
+}
+
 sub cmd_update_vcs_git () {
     my $specsuite;
     if (@ARGV==0 || $ARGV[0] =~ m/^-/) {
@@ -4653,11 +4694,10 @@ sub cmd_update_vcs_git () {
        }
     }
 
-    my $sourcep = parsecontrol 'debian/control', 'debian/control';
-    $package = getfield $sourcep, 'Source';
+    package_from_d_control();
     my $ctrl;
     if ($specsuite eq '.') {
-       $ctrl = $sourcep;
+       $ctrl = parsecontrol 'debian/control', 'debian/control';
     } else {
        $isuite = $specsuite;
        get_archive_dsc();
@@ -5399,7 +5439,8 @@ sub quiltify ($$$$) {
                print STDERR "$us:  ", $reportnot->($notp), "\n";
            }
            print STDERR "$us: $_\n" foreach @$failsuggestion;
-           fail "quilt fixup naive history linearisation failed.\n".
+           fail
+ "quilt history linearisation failed.  Search \`quilt fixup' in dgit(7).\n".
  "Use dpkg-source --commit by hand; or, --quilt=smash for one ugly patch";
        } elsif ($quilt_mode eq 'smash') {
        } elsif ($quilt_mode eq 'auto') {
@@ -5571,7 +5612,7 @@ END
        if (act_local()) {
            debugcmd "+",@cmd;
            $!=0; $?=-1;
-           failedcmd @cmd if system @cmd and $?!=7;
+           failedcmd @cmd if system @cmd and $?!=7*256;
        } else {
            dryrun_report @cmd;
        }
@@ -6437,7 +6478,7 @@ sub cmd_quilt_fixup {
 
 sub import_dsc_result {
     my ($dstref, $newhash, $what_log, $what_msg) = @_;
-    my @cmd = (@git, qw(update-ref -m), $what_log, $dstref, $newhash);
+    my @cmd = (git_update_ref_cmd $what_log, $dstref, $newhash);
     runcmd @cmd;
     check_gitattrs($newhash, "source tree");