2019-02-16 22:22:30 -08:00
|
|
|
#!/bin/bash
|
|
|
|
|
|
|
|
|
|
usage () {
|
|
|
|
|
echo "USAGE: ./sync-kernel.sh <kernel-repo> <libbpf-repo> [<baseline-commit>]"
|
|
|
|
|
echo ""
|
|
|
|
|
echo "If <baseline-commit> is not specified, it's read from <libbpf-repo>/CHECKPOINT-COMMIT"
|
|
|
|
|
exit 1
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
LINUX_REPO=${1-""}
|
|
|
|
|
LIBBPF_REPO=${2-""}
|
|
|
|
|
|
|
|
|
|
if [ -z "${LINUX_REPO}" ]; then
|
|
|
|
|
usage
|
|
|
|
|
fi
|
|
|
|
|
if [ -z "${LIBBPF_REPO}" ]; then
|
|
|
|
|
usage
|
|
|
|
|
fi
|
|
|
|
|
|
|
|
|
|
set -eu
|
|
|
|
|
|
|
|
|
|
WORKDIR=$(pwd)
|
|
|
|
|
trap "cd ${WORKDIR}; exit" INT TERM EXIT
|
|
|
|
|
|
2019-03-02 21:19:17 -08:00
|
|
|
echo "WORKDIR: ${WORKDIR}"
|
|
|
|
|
echo "LINUX REPO: ${LINUX_REPO}"
|
|
|
|
|
echo "LIBBPF REPO: ${LIBBPF_REPO}"
|
2019-02-16 22:22:30 -08:00
|
|
|
|
|
|
|
|
SUFFIX=$(date --utc +%Y-%m-%dT%H-%M-%S.%3NZ)
|
|
|
|
|
BASELINE_COMMIT=${3-$(cat ${LIBBPF_REPO}/CHECKPOINT-COMMIT)}
|
|
|
|
|
|
|
|
|
|
# Use current kernel repo HEAD as a source of patches
|
|
|
|
|
cd ${LINUX_REPO}
|
2019-03-02 21:19:17 -08:00
|
|
|
TIP_SYM_REF=$(git symbolic-ref -q --short HEAD || git rev-parse HEAD)
|
|
|
|
|
TIP_COMMIT=$(git rev-parse HEAD)
|
|
|
|
|
BASELINE_TAG=libbpf-baseline-${SUFFIX}
|
|
|
|
|
TIP_TAG=libbpf-tip-${SUFFIX}
|
|
|
|
|
VIEW_TAG=libbpf-view-${SUFFIX}
|
|
|
|
|
LIBBPF_SYNC_TAG=libbpf-sync-${SUFFIX}
|
2019-02-16 22:22:30 -08:00
|
|
|
|
|
|
|
|
# Squash state of kernel repo at baseline into single commit
|
2019-03-02 21:19:17 -08:00
|
|
|
SQUASH_BASE_TAG=libbpf-squash-base-${SUFFIX}
|
|
|
|
|
SQUASH_TIP_TAG=libbpf-squash-tip-${SUFFIX}
|
|
|
|
|
SQUASH_COMMIT=$(git commit-tree ${BASELINE_COMMIT}^{tree} -m "BASELINE SQUASH ${BASELINE_COMMIT}")
|
|
|
|
|
|
|
|
|
|
echo "SUFFIX: ${SUFFIX}"
|
|
|
|
|
echo "BASELINE COMMIT: $(git log --pretty=oneline --no-walk ${BASELINE_COMMIT})"
|
|
|
|
|
echo "TIP COMMIT: $(git log --pretty=oneline --no-walk ${TIP_COMMIT})"
|
|
|
|
|
echo "SQUASH COMMIT: ${SQUASH_COMMIT}"
|
|
|
|
|
echo "BASELINE TAG: ${BASELINE_TAG}"
|
|
|
|
|
echo "TIP TAG: ${TIP_TAG}"
|
|
|
|
|
echo "SQUASH BASE TAG: ${SQUASH_BASE_TAG}"
|
|
|
|
|
echo "SQUASH TIP TAG: ${SQUASH_TIP_TAG}"
|
|
|
|
|
echo "VIEW TAG: ${VIEW_TAG}"
|
|
|
|
|
echo "LIBBPF SYNC TAG: ${LIBBPF_SYNC_TAG}"
|
|
|
|
|
|
|
|
|
|
TMP_DIR=$(mktemp -d)
|
|
|
|
|
echo "TEMP DIR: ${TMP_DIR}"
|
|
|
|
|
echo "PATCHES+COVER: ${TMP_DIR}/patches"
|
|
|
|
|
echo "PATCHSET: ${TMP_DIR}/patchset.patch"
|
|
|
|
|
|
|
|
|
|
git branch ${BASELINE_TAG} ${BASELINE_COMMIT}
|
|
|
|
|
git branch ${TIP_TAG} ${TIP_COMMIT}
|
|
|
|
|
git branch ${SQUASH_BASE_TAG} ${SQUASH_COMMIT}
|
|
|
|
|
git checkout -b ${SQUASH_TIP_TAG} ${SQUASH_COMMIT}
|
|
|
|
|
|
|
|
|
|
# Cherry-pick new commits onto squashed baseline commit
|
2019-07-01 18:31:31 -07:00
|
|
|
LIBBPF_PATHS=(tools/lib/bpf tools/include/uapi/linux/{bpf_common.h,bpf.h,btf.h,if_link.h,if_xdp.h,netlink.h} tools/include/tools/libc_compat.h)
|
2019-03-28 16:40:41 -07:00
|
|
|
|
|
|
|
|
LIBBPF_NEW_MERGES=$(git rev-list --merges --topo-order --reverse ${BASELINE_TAG}..${TIP_TAG} ${LIBBPF_PATHS[@]})
|
|
|
|
|
for LIBBPF_NEW_MERGE in ${LIBBPF_NEW_MERGES}; do
|
|
|
|
|
printf "MERGE:\t" && git log --oneline -n1 ${LIBBPF_NEW_MERGE}
|
|
|
|
|
MERGE_CHANGES=$(git log --format='' -n1 ${LIBBPF_NEW_MERGE} | wc -l)
|
|
|
|
|
if ((${MERGE_CHANGES} > 0)); then
|
|
|
|
|
echo "Merge is non empty, aborting!.."
|
|
|
|
|
exit 3
|
|
|
|
|
fi
|
|
|
|
|
done
|
|
|
|
|
|
sync-kernel.sh: detect synced commits, interactively resolve conflicts
1. There is one commit ("libbpf: fix btf_dedup equivalence check
handling of different kinds"), which was originally committed into bpf
tree and manually synced into libbpf (it was a critical bug fix). Now
that bpf and bpf-next trees were merged, this causes duplicate commits in
libbpf. To address this, check is added to see if libbpf repo already has
a commit with the same subject and allow to skip it.
2. Just checking by subject is not good enough, as we currently have few
different commits with the same subject "bpf: Sync bpf.h to tools/".
To address this, script now will ask user whether to skip or cherry-pick
commit. This allows for human to double-check the commit and make
informed devision.
3. There is a commit ('bfb35c27c65f bpf: fix whitespace for ENCAP_L2
defines in bpf.h'), which modifies both include/uapi/linux/bpf.h and
tools/include/uapi/linux/bpf.h in the same commit. This break the
sync script, as it doesn't cherry-pick commits that hasn't modified
libbpf files. So at the time that commit bfb35c27c65f is applied, linux
repo is missing some preceding changes to include/uapi/linux/bpf.h. They
would normally be ignored later during repo filtering, but to do
cherry-pick they are necessary. It's hard to fix it automatically, so
script will wait for user to resolve the issue and continue.
Signed-off-by: Andrii Nakryiko <andriin@fb.com>
2019-04-18 15:24:21 -07:00
|
|
|
cd ${WORKDIR} && cd ${LIBBPF_REPO}
|
|
|
|
|
git log --oneline -n500 > ${TMP_DIR}/libbpf_commits.txt
|
|
|
|
|
cd ${WORKDIR} && cd ${LINUX_REPO}
|
|
|
|
|
|
2019-03-28 16:40:41 -07:00
|
|
|
LIBBPF_NEW_COMMITS=$(git rev-list --no-merges --topo-order --reverse ${BASELINE_TAG}..${TIP_TAG} ${LIBBPF_PATHS[@]})
|
2019-03-02 21:19:17 -08:00
|
|
|
for LIBBPF_NEW_COMMIT in ${LIBBPF_NEW_COMMITS}; do
|
sync-kernel.sh: detect synced commits, interactively resolve conflicts
1. There is one commit ("libbpf: fix btf_dedup equivalence check
handling of different kinds"), which was originally committed into bpf
tree and manually synced into libbpf (it was a critical bug fix). Now
that bpf and bpf-next trees were merged, this causes duplicate commits in
libbpf. To address this, check is added to see if libbpf repo already has
a commit with the same subject and allow to skip it.
2. Just checking by subject is not good enough, as we currently have few
different commits with the same subject "bpf: Sync bpf.h to tools/".
To address this, script now will ask user whether to skip or cherry-pick
commit. This allows for human to double-check the commit and make
informed devision.
3. There is a commit ('bfb35c27c65f bpf: fix whitespace for ENCAP_L2
defines in bpf.h'), which modifies both include/uapi/linux/bpf.h and
tools/include/uapi/linux/bpf.h in the same commit. This break the
sync script, as it doesn't cherry-pick commits that hasn't modified
libbpf files. So at the time that commit bfb35c27c65f is applied, linux
repo is missing some preceding changes to include/uapi/linux/bpf.h. They
would normally be ignored later during repo filtering, but to do
cherry-pick they are necessary. It's hard to fix it automatically, so
script will wait for user to resolve the issue and continue.
Signed-off-by: Andrii Nakryiko <andriin@fb.com>
2019-04-18 15:24:21 -07:00
|
|
|
echo "Checking commit '${LIBBPF_NEW_COMMIT}'"
|
|
|
|
|
SYNCED_COMMITS=$(grep -F "$(git log -n1 --pretty=format:%s ${LIBBPF_NEW_COMMIT})" ${TMP_DIR}/libbpf_commits.txt || echo "")
|
|
|
|
|
if [ -n "${SYNCED_COMMITS}" ]; then
|
|
|
|
|
# commit with the same subject is already in libbpf, but it's not 100% the same commit, so check with user
|
|
|
|
|
echo "Commit '$(git log -n1 --oneline ${LIBBPF_NEW_COMMIT})' appears to be already synced into libbpf..."
|
|
|
|
|
echo "Corresponding libbpf commit(s):"
|
|
|
|
|
echo "${SYNCED_COMMITS}"
|
|
|
|
|
read -p "Do you want to skip it? [y/N]: " SHOULD_SKIP
|
|
|
|
|
case "${SHOULD_SKIP}" in
|
|
|
|
|
"y" | "Y")
|
|
|
|
|
echo "Skipping '$(git log -n1 --oneline ${LIBBPF_NEW_COMMIT})'..."
|
|
|
|
|
continue
|
|
|
|
|
;;
|
|
|
|
|
esac
|
|
|
|
|
fi
|
|
|
|
|
# commit hasn't been synced into libbpf yet
|
|
|
|
|
if ! git cherry-pick ${LIBBPF_NEW_COMMIT}; then
|
|
|
|
|
read -p "Cherry-picking '$(git log --oneline -n1 ${LIBBPF_NEW_COMMIT})' failed, please fix manually and press <return> to proceed..."
|
|
|
|
|
fi
|
2019-03-02 21:19:17 -08:00
|
|
|
done
|
|
|
|
|
|
2019-03-19 09:37:23 -07:00
|
|
|
LIBBPF_TREE_FILTER=' \
|
|
|
|
|
mkdir -p __libbpf/include/uapi/linux __libbpf/include/tools && \
|
|
|
|
|
git mv -kf tools/lib/bpf __libbpf/src && \
|
|
|
|
|
git mv -kf tools/include/uapi/linux/{bpf_common.h,bpf.h,btf.h,if_link.h,if_xdp.h,netlink.h} \
|
|
|
|
|
__libbpf/include/uapi/linux && \
|
|
|
|
|
git mv -kf tools/include/tools/libc_compat.h __libbpf/include/tools && \
|
|
|
|
|
git rm --ignore-unmatch -f __libbpf/src/{Makefile,Build,test_libbpf.cpp,.gitignore} \
|
2019-03-02 21:19:17 -08:00
|
|
|
'
|
|
|
|
|
# Move all libbpf files into __libbpf directory.
|
|
|
|
|
git filter-branch --prune-empty -f --tree-filter "${LIBBPF_TREE_FILTER}" ${SQUASH_TIP_TAG} ${SQUASH_BASE_TAG}
|
|
|
|
|
# Make __libbpf a new root directory
|
|
|
|
|
git filter-branch --prune-empty -f --subdirectory-filter __libbpf ${SQUASH_TIP_TAG} ${SQUASH_BASE_TAG}
|
|
|
|
|
|
|
|
|
|
# If there are no new commits with libbpf-related changes, bail out
|
|
|
|
|
COMMIT_CNT=$(git rev-list --count ${SQUASH_BASE_TAG}..${SQUASH_TIP_TAG})
|
2019-02-16 22:22:30 -08:00
|
|
|
if ((${COMMIT_CNT} <= 0)); then
|
|
|
|
|
echo "No new changes to apply, we are done!"
|
|
|
|
|
exit 2
|
|
|
|
|
fi
|
|
|
|
|
|
|
|
|
|
# Exclude baseline commit and generate nice cover letter with summary
|
2019-03-02 21:19:17 -08:00
|
|
|
git format-patch ${SQUASH_BASE_TAG}..${SQUASH_TIP_TAG} --cover-letter -o ${TMP_DIR}/patches
|
|
|
|
|
# Now generate single-file patchset w/o cover to apply on top of libbpf repo
|
|
|
|
|
git format-patch ${SQUASH_BASE_TAG}..${SQUASH_TIP_TAG} --stdout > ${TMP_DIR}/patchset.patch
|
2019-02-16 22:22:30 -08:00
|
|
|
|
2019-03-02 21:19:17 -08:00
|
|
|
# Now is time to re-apply libbpf-related linux patches to libbpf repo
|
|
|
|
|
cd ${WORKDIR} && cd ${LIBBPF_REPO}
|
|
|
|
|
git checkout -b ${LIBBPF_SYNC_TAG}
|
|
|
|
|
git am --committer-date-is-author-date ${TMP_DIR}/patchset.patch
|
2019-02-16 22:22:30 -08:00
|
|
|
|
|
|
|
|
# Use generated cover-letter as a template for "sync commit" with
|
|
|
|
|
# baseline and checkpoint commits from kernel repo (and leave summary
|
|
|
|
|
# from cover letter intact, of course)
|
2019-03-02 21:19:17 -08:00
|
|
|
echo ${TIP_COMMIT} > CHECKPOINT-COMMIT && \
|
|
|
|
|
git add CHECKPOINT-COMMIT && \
|
|
|
|
|
awk '/\*\*\* BLURB HERE \*\*\*/ {p=1} p' ${TMP_DIR}/patches/0000-cover-letter.patch | \
|
2019-02-16 22:22:30 -08:00
|
|
|
sed "s/\*\*\* BLURB HERE \*\*\*/\
|
|
|
|
|
sync: latest libbpf changes from kernel\n\
|
|
|
|
|
\n\
|
|
|
|
|
Syncing latest libbpf commits from kernel repository.\n\
|
|
|
|
|
Baseline commit: ${BASELINE_COMMIT}\n\
|
2019-03-02 21:19:17 -08:00
|
|
|
Checkpoint commit: ${TIP_COMMIT}/" | \
|
2019-02-16 22:22:30 -08:00
|
|
|
git commit --file=-
|
|
|
|
|
|
2019-03-02 21:19:17 -08:00
|
|
|
echo "SUCCESS! ${COMMIT_CNT} commits synced."
|
|
|
|
|
|
|
|
|
|
echo "Verifying Linux's and Github's libbpf state"
|
2019-03-19 09:37:23 -07:00
|
|
|
LIBBPF_VIEW_PATHS=(src include/uapi/linux/{bpf_common.h,bpf.h,btf.h,if_link.h,if_xdp.h,netlink.h} include/tools/libc_compat.h)
|
2019-03-02 21:19:17 -08:00
|
|
|
LIBBPF_VIEW_EXCLUDE_REGEX='^src/(Makefile|Build|test_libbpf.cpp|\.gitignore)$'
|
|
|
|
|
|
|
|
|
|
cd ${WORKDIR} && cd ${LINUX_REPO}
|
|
|
|
|
LINUX_ABS_DIR=$(pwd)
|
|
|
|
|
git checkout -b ${VIEW_TAG} ${TIP_COMMIT}
|
|
|
|
|
git filter-branch -f --tree-filter "${LIBBPF_TREE_FILTER}" ${VIEW_TAG}^..${VIEW_TAG}
|
|
|
|
|
git filter-branch -f --subdirectory-filter __libbpf ${VIEW_TAG}^..${VIEW_TAG}
|
|
|
|
|
git ls-files -- ${LIBBPF_VIEW_PATHS[@]} > ${TMP_DIR}/linux-view.ls
|
|
|
|
|
|
|
|
|
|
cd ${WORKDIR} && cd ${LIBBPF_REPO}
|
|
|
|
|
GITHUB_ABS_DIR=$(pwd)
|
|
|
|
|
git ls-files -- ${LIBBPF_VIEW_PATHS[@]} | grep -v -E "${LIBBPF_VIEW_EXCLUDE_REGEX}" > ${TMP_DIR}/github-view.ls
|
|
|
|
|
|
|
|
|
|
echo "Comparing list of files..."
|
|
|
|
|
diff ${TMP_DIR}/linux-view.ls ${TMP_DIR}/github-view.ls
|
|
|
|
|
echo "Comparing file contents..."
|
|
|
|
|
for F in $(cat ${TMP_DIR}/linux-view.ls); do
|
|
|
|
|
diff "${LINUX_ABS_DIR}/${F}" "${GITHUB_ABS_DIR}/${F}"
|
|
|
|
|
done
|
|
|
|
|
echo "Contents appear identical!"
|
|
|
|
|
|
|
|
|
|
echo "Cleaning up..."
|
|
|
|
|
rm -r ${TMP_DIR}
|
|
|
|
|
cd ${WORKDIR} && cd ${LINUX_REPO}
|
|
|
|
|
git checkout ${TIP_SYM_REF}
|
|
|
|
|
git branch -D ${BASELINE_TAG} ${TIP_TAG} ${SQUASH_BASE_TAG} ${SQUASH_TIP_TAG} ${VIEW_TAG}
|
|
|
|
|
|
|
|
|
|
cd ${WORKDIR}
|
|
|
|
|
echo "DONE."
|
2019-02-16 22:22:30 -08:00
|
|
|
|