-
Oswald Buddenhagen authored
Change-Id: I670423c6001e2a504df8be80b42ee88566ad3baa Reviewed-by:
Oswald Buddenhagen <oswald.buddenhagen@digia.com>
e2f973a8
#!/usr/bin/perl -w
####################################################################################################
#
# git-qt-grafts
#
# Sets up the proper grafts for a Qt repository
#
# Copyright (C) 2013 Digia Plc and/or its subsidiary(-ies).
# Contact: http://www.qt-project.org/legal
#
####################################################################################################
use File::Basename;
use Cwd 'abs_path';
use strict;
my $history_location;
# Syntax: fileContents(filename)
# Returns: String with contents of the file, or empty string if file
# doens't exist.
sub fileContents {
my ($filename) = @_;
my $filecontents = "";
if (-e $filename) {
my $FD;
open($FD, "< $filename") || die "Could not open $filename for reading, read block?";
local $/;
binmode $FD;
$filecontents = <$FD>;
close $FD;
}
return $filecontents;
}
sub fileContains {
my ($filename, $text) = @_;
# purposely not using perl grep here
foreach my $line (split /\n/, fileContents("$filename")) {
return 1 if ("$line" eq "$text");
}
return 0;
}
sub showUsage {
my $prg = basename($0);
print "Usage: $prg <path to Qt history>:\n";
}
while ( @ARGV ) {
my $arg = shift @ARGV;
if ($arg eq "-?" || $arg eq "-h" || $arg eq "-help" || $arg eq "?") {
showUsage();
exit 0;
} elsif (!$history_location) {
$history_location = $arg;
} else {
print "Unknown option: $arg\n\n";
showUsage();
exit 1;
}
}
# Get current git-dir
my $git_dir = `git rev-parse --git-dir`;
chomp $git_dir;
if (!$git_dir) {
print "Cannot find any Git dir!\n";
exit 1;
}
7172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140
# validate path for history repo
if (!$history_location || !-e $history_location) {
print "You need to provide a path to the monolithic Qt repo!\n";
exit 1;
}
my $history_git_dir = `cd $history_location && git rev-parse --git-dir`;
chomp $history_git_dir;
if (!$history_git_dir || !-e "$history_location/$history_git_dir/objects") {
print "Monolithic Qt repo path is not a valid Git repo!\n";
exit 1;
}
$history_git_dir = abs_path("$history_location/$history_git_dir");
my $history_alternates_objects = "$history_git_dir/objects";
# check if we already point to this alternate object store
my $git_alternates_file = "$git_dir/objects/info/alternates";
my $found_alternate = fileContains($git_alternates_file, $history_alternates_objects);
# get first commit SHA1 of this repo which mentions branching from a commit
my $GIT_REVLIST;
my $git_pid = open($GIT_REVLIST, "git rev-list --reverse --grep='Branched from .*at commit' HEAD |")
or die ("Failed to launch Git");
my @commits;
while (<$GIT_REVLIST>) {
chomp;
push(@commits, $_);
}
close($GIT_REVLIST);
my $found_any_grafts = 0;
my $graft_file = "$git_dir/info/grafts";
my @graft_lines;
foreach my $commit (@commits) {
# find the graft point which the commit mentions
my $commit_msg = `git show -s --format=%b $commit`;
my $graft_to_commit = $commit_msg;
$graft_to_commit =~ s/^.+Branched from .+at commit\n([a-f0-9]+)\n.*/$1/s;
next if (!$graft_to_commit || $graft_to_commit eq $commit_msg);
# Preserve any existing parents of the commit.
my @existing_parents;
my $GIT_CAT_FILE;
open($GIT_CAT_FILE, "git cat-file commit $commit |") or die ("Failed to launch Git");
while (<$GIT_CAT_FILE>) {
if (/^parent ([0-9a-z]{40})/i) {
push(@existing_parents, $1);
}
}
close($GIT_CAT_FILE);
# check that we don't already have this graft already setup
my $graft_line = "$commit $graft_to_commit";
$graft_line .= " " . join(" ", @existing_parents) if (@existing_parents);
my $found_graft = fileContains($graft_file, $graft_line);
if ($found_graft) {
print "Graft for $commit already exists. Skipping...\n";
$found_any_grafts = 1;
next;
}
# verify that alternate object store contains the commit we want to graft to
if (system("cd $history_location && git cat-file -e $graft_to_commit") != 0) {
print "History repo ($history_location) does not contain commit $graft_to_commit!\n";
print "Skipping this graft...\n";
next;
}
print "Grafted $commit -> $graft_to_commit\n";
push(@graft_lines, $graft_line);
141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185
$found_any_grafts = 1;
}
if (!$found_any_grafts) {
print "This repo does not refer to a graft point, so no grafts added!\n";
exit 0;
}
# if our alternates file didn't contain the "history repo" path already
# add its path now
if (!$found_alternate) {
my $ALTERNATES_FILE;
open($ALTERNATES_FILE, ">> $git_alternates_file") || die "Could not open $git_alternates_file for writing, wrong permissions?";
print $ALTERNATES_FILE "$history_alternates_objects\n";
# Add alternates from alternates file in the history repo, in case it has additional alternates.
my $HISTORY_ALTERNATES_FILE;
if (open($HISTORY_ALTERNATES_FILE, "< $history_git_dir/objects/info/alternates")) {
print("Reusing existing alternates in history repository\n");
while (<$HISTORY_ALTERNATES_FILE>) {
chomp;
print $ALTERNATES_FILE $_ if (!fileContains($git_alternates_file, $_));
}
close($HISTORY_ALTERNATES_FILE);
}
close($ALTERNATES_FILE);
}
# Add graft lines from graft file in the history repo, in case it has additional grafts.
my $HISTORY_GRAFT_FILE;
if (open($HISTORY_GRAFT_FILE, "< $history_git_dir/info/grafts")) {
print("Reusing existing grafts in history repository\n");
while (<$HISTORY_GRAFT_FILE>) {
chomp;
push(@graft_lines, $_) if (!fileContains($graft_file, $_));
}
close($HISTORY_GRAFT_FILE);
}
# add graft
if (@graft_lines) {
my $GRAFT_FILE;
open($GRAFT_FILE, ">> $graft_file") || die "Could not open $graft_file for writing, wrong permissions?";
print $GRAFT_FILE join("\n", @graft_lines) . "\n";
close($GRAFT_FILE);
}