Skip to content

Instantly share code, notes, and snippets.

@Hoikas
Forked from cwalther/binkbegone.sh
Created December 11, 2012 05:22
Show Gist options
  • Save Hoikas/4256098 to your computer and use it in GitHub Desktop.
Save Hoikas/4256098 to your computer and use it in GitHub Desktop.
CWE-ou & H-uru/Plasma History Rewrite
#!/bin/bash
if test "x$1" == x -o "x$2" == x; then
echo "Usage: $0 <original CWE-ou repo> <original H-uru/Plasma repo>"
exit 1
fi
if test -e old-hg -o -e uncorrupt-git -o -e uncorrupt-hg -o -e filemap1 -o -e filemap2 -o -e filtered-hg -o -e filtered-git; then
echo "Output files/folders exist."
read -p "OK to delete? (y/n) " REPLY
if test "x$REPLY" != "xy"; then
exit 1
fi
set -x
rm -rf old-hg uncorrupt-git uncorrupt-hg filemap1 filemap2 filtered-hg filtered-git
fi
set -x
set -e
#### OU part
# pull the first few revisions from which we also want to remove the empty .hgignore file
hg init old-hg
cd old-hg
hg pull -r e106bb4cef24 "$1"
cd ..
# fix the corrupted 'Merge "Open source re-licensing" into OpenUru base' commit so that it will successfully round-trip-convert with Hg-Git (the way of doing it completely in Mercurial I showed in http://forums.openuru.org/viewtopic.php?p=5024#p5024 no longer works with Mercurial 2.2 and later due to http://selenic.com/pipermail/mercurial-devel/2012-April/039570.html - do it by pushing to Git and back instead)
git init --bare uncorrupt-git
cd old-hg
hg push ../uncorrupt-git
hg bookmark --delete master
cd ../uncorrupt-git
# pull back in pieces to get the commits in the same order as in the original repository (not strictly necessary, since it doesn't affect the commit ids, but it makes visual comparison easier)
git branch ob1 a2f42c3fdce88da8c538570a666c07359670edd8
git branch ob2 5c3cab7f4f1134925283dd526233131856b7a894
cd ..
hg init uncorrupt-hg
cd uncorrupt-hg
# this may error out with "ValueError: 20-byte hash required", you can ignore that
hg pull -r ob1 ../uncorrupt-git || true
hg pull -r ob2 ../uncorrupt-git
hg pull -r master ../uncorrupt-git
hg gclear
# remove the tags created by Hg-Git, otherwise 'hg convert' will fabricate commits that put them into .hgtags
rm .hg/git-remote-refs
rm .hg/git-tags
hg bookmark --delete ob1
hg bookmark --delete ob2
hg bookmark --delete master
cd ..
# eradicate the Bink files as well as the empty .hgignore
cat <<EOF > filemap2
exclude MOULOpenSourceClientPlugin/Plasma20/Sources/Plasma/FeatureLib/pfSurface/plLayerBink.cpp
exclude MOULOpenSourceClientPlugin/Plasma20/Sources/Plasma/PubUtilLib/plPipeline/plBinkPlayer.cpp
exclude MOULOpenSourceClientPlugin/Plasma20/Sources/Tools/MaxPlasmaMtls/plBinkBitmap.cpp
EOF
cp filemap2 filemap1
echo "exclude .hgignore" >> filemap1
hg convert --filemap filemap1 uncorrupt-hg filtered-hg
# rewrite the list of already converted revisions, replacing ids from uncorrupt-hg by those from old-hg, so that we can continue converting from old-hg
sed -e s/050a1be2ccf20aafa2706cadc1c01a7a8115751a/f7cecd95cba5b02a57d48f8520256254c5d5b44e/ -e s/26bd467e4f79798f48160de2f5f34398571f5237/fe3d8bed6097cfb7a79c22d436168238ab79cfb3/ -e s/85629ffd6bd3ab30a2a67426b2056e88f1c22de3/2731d8112948c405da4ee5e3ecd8a3ae6c9e0ddb/ -e s/a1ef2ea16724cf5b3a11f7ca2b351b9f3e2986b7/7e48b9bca28a775701e6cff1d5f5bc8bd0d0f024/ -e s/7cf3077f939a00457aa4c7a5860b9e64ea42b246/63ca11404699ec52cfa47e34144b966ed978964a/ -e s/15741fa74e8ad85085ce6627e2ce33cd2610eeaa/e4a36a01fc74834a92cfaf2f35c8c96f0e2eaf07/ -e s/3d3545d1dd00dc9269e954a05e2e59a1b4592248/e106bb4cef2473b41b67f1f304b50f40579b1353/ filtered-hg/.hg/shamap > newshamap
mv newshamap filtered-hg/.hg/shamap
# add the rest of CWE-ou (now with its real .hgignore)
cd old-hg
hg pull -r 2a23f5511857 "$1"
cd ..
hg convert --filemap filemap2 old-hg filtered-hg
rm -rf filemap1 filemap2 uncorrupt-hg uncorrupt-git
# check
if test "x`hg -R filtered-hg log --template="{node}\n" -r 129`" != "xc0fa2386a92d7ff774b5033bf5560c52ea36324c"; then
set +x
echo
echo "Something unexpected happened in the conversion. OU/Hg Revision 129 \"Merged in"
echo "Skoader/cwe-ou/window-size (pull request #18)\" was expected to have id"
echo "c0fa2386a92d7ff774b5033bf5560c52ea36324c, got"
hg -R filtered-hg log -r 129
echo
echo "Please compare to the published solution to figure out why, or contact Christian Walther."
echo
set -x
fi
# done with the OU side!
# to check file trees:
# for ((i=0; i<130; i++)); do echo $i; hg up $i -R old-hg; hg up $i -R filtered-hg; diff -qaur -x .hg old-hg filtered-hg > actualdiff; if ! (cmp -s expecteddiff1 actualdiff || cmp -s expecteddiff2 actualdiff || cmp -s expecteddiff3 actualdiff); then diff -u expecteddiff2 actualdiff; fi; done
#### H-uru part
# get the new common leg, with correct committer names, from Mercurial
git init --bare filtered-git
hg -R filtered-hg bookmark -r 6 divergence
hg -R filtered-hg push -r divergence filtered-git
# get the old H-uru/Plasma commits
cd filtered-git
git fetch "$2" master
git branch master FETCH_HEAD
# set up grafts:
# - graft descendants of old OU leg onto new common leg
# - graft descendants of old H-uru leg onto new common leg
# - eliminate merging of OU leg (cut off its second parent, filter-branch will eliminate it because it's a no-op with respect to the first parent)
cat <<EOF > info/grafts
29b76601ad294bca52b6be462daec2684cd6042b 3bb1281fd1db11404de5baf22612d726216a5c11
ececa5fa9937d27e4f8cbbfe441977cd44aeb439 3bb1281fd1db11404de5baf22612d726216a5c11
71d81a580debf4499c7ce28418cbacc40495bfa8 0671b2825a3c22721c1d255ae5e950ae9dca523f
EOF
# filter:
# - remove Bink files
# - remove .hgignore if it is empty (on OU leg)
# - on commits that move files around, add move information for Mercurial (note that the code here wouldn't work correctly on commits that move files and already have --HG-- information, but there are none of these in H-uru/Plasma)
# - skip revisions up to 3bb1281 because some among them have author/committer name a'moaca', which filter-branch would mangle to a'moaca
git filter-branch --index-filter 'git rm --cached --ignore-unmatch */plLayerBink.cpp */plBinkPlayer.cpp */plBinkBitmap.cpp; test `git show :.hgignore 2>/dev/null | wc -c` == 0 && git rm --cached --ignore-unmatch .hgignore' --msg-filter 'cat && git diff --staged --name-status -M75 -l5000 $GIT_COMMIT^ | grep ^R | sed "s/^R[0-9]* \([^ ]*\) \(.*\)$/rename : \1 => \2/" > ../renames && test `cat ../renames | wc -c` -ne 0 && echo && echo "--HG--" && cat ../renames; rm ../renames' --prune-empty --tag-name-filter cat -- --all --not 3bb1281
rm info/grafts
rm -r refs/original
# check
if test "x`git log --pretty=format:%H master^! | cat`" != "x3a6cf87d7581e10a3d72b7eccc27c21fb26db4df"; then
set +x
echo
echo "Something unexpected happened in the conversion. H-uru/Git revision master \"Merge"
echo "pull request #229 from Hoikas/locdata-strings\" was expected to have id"
echo "3a6cf87d7581e10a3d72b7eccc27c21fb26db4df, got"
git log master^! | cat
echo "Please compare to the published solution to figure out why, or contact Christian Walther."
echo
set -x
fi
cd ..
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment