Linux OMAP integration tree

= About this page =

This is a collection of notes regarding the management of the TI OMAP Linux kernel integration trees.
 * The OMAP3 public kernel integration tree can be found here: http://dev.omapzoom.org/?p=integration/kernel-omap3.git
 * The OMAP4 public kernel integration tree can be found here: http://dev.omapzoom.org/?p=integration/kernel-omap4.git

TI is maintaining such integration trees in order to release the most up-to-date source code from various maintainers. All the source code is based on linux-omap kernel development tree but some critical OMAP sub systems such as camera, display, ... have specific maintainers and it is more appropriate for TI to get the latest code from these trees instead of linux-omap.

= Quick instructions =

Here are some quick instructions in case you are already familiar with Git and Linux kernel development. Otherwise please jump to the next section for a much more detailed version.

So basically, the process of making a new release can be summarized as:
 * 1) reset your tree to a specific version of linux-omap
 * 2) rebase all development trees to this linux-omap commit
 * 3) merge all development trees one by one into your topic branch, resolve conflicts whenever apply
 * 4) fix up defconfig so that all necessary drivers and PM are enabled
 * 5) apply set of manual patches if required
 * 6) apply a tag and push to the public tree, in the master branch

For example the following git commands can be used to realize a release:

$ git checkout -b new_release abcd1234 $ git remote update # assuming you've already set up all development trees as remote $ for each development tree , do    git merge /master git commit -s $ edit arch/arm/config/omap3_zoom2_defconfig or make menuconfig $ for each required patch, do    git am or git apply $ git tag  -a 'Linux OMAP integration release for L23.18' $ git push --tags origin +new_release:master

For every new release the history is reset to latest linux-omap, to some extent this process is similar to the linux-next process (http://lwn.net/Articles/287155/ or http://linux.f-seidel.de/linux-next/pmwiki/).

= Git material =

Git is a very powerful tool and it requires some time to get used to it. Here are some very good material available that are *very helpful*:


 * http://git-scm.com/documentation
 * http://excess.org/article/2008/07/ogre-git-tutorial/
 * http://www.youtube.com/watch?v=4XpnKHJAok8
 * http://www.amazon.com/Version-Control-Git-collaborative-development/dp/0596520123/ref=pd_sim_b_7
 * http://progit.org/book/

= Setup the environment =

Ideally you should be using a dedicated local integration tree for 'sync' tree activities, instead of using an existing development tree. Once a local tree has been setup, it can be used for all monthly releases, it does not have to be created for each release.

Creating a local integration tree
It is recommended to setup this local integration as a clone of the original tree from dev.omapzoom.org, such as:

$ git clone git://dev.omapzoom.org/pub/scm/integration/kernel-omap3.git

Adding remotes
Then for convenience, you should add all the feature branch trees as 'remote' in your local tree so that you can easily fetch some or all of them, and merge as needed. So for each feature tree, you would do:

$ git remote add git://xxx.yyy/ .git

For example, the following commands setup your remotes with DSS, V4l2, Bridge, Camera and PM:

$ git remote add pm git://git.kernel.org/pub/scm/linux/kernel/git/khilman/linux-omap-pm.git $ git remote add camera git://dev.omapzoom.org/pub/scm/saaguirre/linux-omap-camera.git $ git remote add bridge git://dev.omapzoom.org/pub/scm/tidspbridge/kernel-dspbridge.git $ git remote add dss http://www.bat.org/~tomba/git/linux-omap-dss.git $ git remote add video git://arago-project.org/git/people/vaibhav/ti-psp-omap-video.git

It is also convenient to define another remote for the original l-o tree, such as:

$ git remote add -t master linux-omap git://git.kernel.org/pub/scm/linux/kernel/git/tmlind/linux-omap-2.6.git

Note that for this one we are only interested in 'master' branch.

The nice thing with remotes is that it allows you to fetch your remotes' commits into your local tree before the merge, it can be useful sometimes as we will see later. Another advantage is that all remotes' branches will also show up in your local tree.

Once all remotes are defined, your .git/config file should look like this:

[remote "origin"] url = git://git.tif.ti.com/dev.omapzoom.org/integration/kernel-omap3.git fetch = +refs/heads/*:refs/remotes/origin/* [branch "master"] remote = origin merge = refs/heads/master [remote "linux-omap"] url = git://git.kernel.org/pub/scm/linux/kernel/git/tmlind/linux-omap-2.6.git fetch = +refs/heads/master:refs/remotes/linux-omap/master [remote "pm"] url = git://git.kernel.org/pub/scm/linux/kernel/git/khilman/linux-omap-pm.git fetch = +refs/heads/*:refs/remotes/pm/* [remote "camera"] url = git://dev.omapzoom.org/pub/scm/saaguirre/linux-omap-camera.git fetch = +refs/heads/*:refs/remotes/camera/* [remote "bridge"] url = git://dev.omapzoom.org/pub/scm/tidspbridge/kernel-dspbridge.git fetch = +refs/heads/*:refs/remotes/bridge/* ... ...

And you can now fetch all new commits with git remote update, or just fetch from a given remote, for example: git fetch bridge. Once this is done, you can check all remotes' branches, with git branch -r, and it should show something like this:

bridge/bridge-pm-2.6.28 bridge/bridge-pm-2.6.29 bridge/bridge-pm-2.6.30 bridge/bridge-pm-2.6.31 bridge/development-APG bridge/iommu-staging bridge/mailbox-staging bridge/master camera/android-omap-camdevel camera/android-omap-v2.6.29 camera/devel camera/devel-pullint-rc1 camera/dss camera/master camera/master-fixes ... ...

Alternatively, instead of fetching all remotes' branches, you can select which one you are interested into.

= Start a new kernel integration =

Whenever it is time to start a new integration, it is important to decide which l-o commit ID will be the baseline. Once this is decided, you must ensure that all the feature branch trees are already on this baseline. For each feature branch tree, you can have various situations:


 * 1) Feature branch tree is on the correct l-o commit or an older one. In this case there should not be any major problem when merging.
 * 2) Feature branch tree is on a newer l-o commit. In this case you will need to cherry-pick the patches otherwise you will bring new l-o patches that might break other feature branch trees. Another option is to request the feature branch tree owner to provide a specific 'head' rebased on this older l-o commit.

Now it is time to start merging. There are two different options:


 * 1) If you decided to use the remote and have all remotes' branches already fetch, then we will use git merge to merge from local commits
 * 2) If you decided not to fetch all remotes commits, then you can use git pull that will first fetch and then merge the remotes' commits.

Merging from already fetched commits
This is the preferred option, since having all commits already fetched will allow you to inspect 'feature branches' easily.

Inspecting remote branches
There are several git</tt> commands which are really handy to inspect and compare the content of the branches fetched into your local tree. Note that these commands will show you the content of the branches in your current tree. If commits have been done in the remote trees you won't see them until the next time you fetch.


 * git show video/pm</tt> will show you the tip of the video/pm</tt> branch.
 * git log video/pm</tt> will show you the history of the video/pm</tt> branch.
 * git show-branch master video/pm</tt> is a very useful command. It shows the commit graph of master</tt> and video/pm</tt>. Basically it shows each commit that are either or master</tt> or on video/pm</tt>. History is shown until a common parent commit is found. It is very useful to find on which l-o commit a feature branch tree is based. For example if all commits displayed are only on the feature branch and if the common parent is the l-o commit ID that this sync release is based on, then everything looks good! and the merge will be trivial. Then you can also use this command to compare two feature branches against each other... So this command alone will give a good estimate of the complexity of the sync release!

Merging branches
Git is very powerful at merging branches. When merging, git will be able to locate the commits that need to be merged and the one that don't need because there are already present. In general git merges happen without user interaction. When there is conflict, git will leave files as 'unmerged' in your tree, and you will need to fix the conflicts manually.

The git merge command will always merge into the current branch. As such the first thing to do is to create a new branch which will be used for this sync release. This branch will be based on the l-o commit that we picked for this release. So you first need to ensure that you fetched l-o locally, let's say in linux-omap/master</tt>, then you can run:

$ git checkout -b l-o-sync linux-omap/master

Note that if you don't base off the tip of master, then you can do:

$ git checkout -b l-o-sync abcd1224

Then you will successively merge each feature branch, for example:

git merge pm/pm git merge camera/devel git merge bridge/bridge-pm-2.6.31 ...

There are two possibilities for a git merge:


 * 1) There is no merge conflict. In this case all commits are imported in your current integration branch. Some trivial merges might have been done automatically by git.
 * 2) There are conflicts. In this case some files are left 'unmerged' (when you run git status</tt>). In this case you will need to:
 * 3) edit these 'unmerged' files and fix the conflicts. You can locate merge conflict by searching the the following pattern: >>>>>>>></tt>
 * 4) stage the modified files in the index once conflicts are fixed, with git add filexxx</tt>
 * 5) once all conflicts are merged, commit your merge with git commit -s</tt> and check/update the commit message as needed. Note that -s</tt> is used to sign off your commit which is recommended.

Pulling remotes' commits
Instead of setting up the 'remotes' as recommended earlier, it is perfectly fine to directly pull changes from remote trees. In such case you won't be able to inspect the feature branch trees in details, but this is your choice!

To pull each feature branch trees, you still need first to create a new branch for this integration task, then you can run the following commands:

git pull git://dev.omapzoom.org/pub/scm/tidspbridge/kernel-dspbridge.git bridge-pm-2.6.31 git pull git://dev.omapzoom.org/pub/scm/saaguirre/linux-omap-camera.git devel ...

Git will first fetch the necessary commits from the remote trees, and then run the merge. It is important to notice that git pull</tt> is strictly equivalent to <tt>git fetch</tt> and then <tt>git merge</tt>. You will have the same merge conflicts, and they must be fixed in a similar manner!

Merging a specific commit ID
Sometimes, you will need to merge a commit ID which is not the tip of an existing head. However <tt>git pull</tt> only allows you to merge the tip of a head. In such a case, you will need to fetch all commits first into your local tree in a separate branch, such as <tt>git fetch git://git.kernel.org/pub/scm/linux/kernel/git/tmlind/linux-omap-2.6.git omap4:refs/heads/test-omap4</tt>. In this case all commits from the branch <tt>omap4</tt> in Tony's tree are fetched into your local tree, and the local branch <tt>test-omap4</tt> is created.

Once the remote branch is fetched, you can merge a specific commit ID using the <tt>git merge</tt> command since this command allows you to specify a commit ID instead of a branch name: <tt>git merge abcd1234</tt>.

Apply manual patches
Very likely for any given 'sync' tree you will end up with some specific patches that must be applied. Either because of an unpredicted conflict between two feature branches, or because of a missing feature, or whatever... The patch can be applied in several ways:


 * 1) If the patch is available on a public git tree, then it can be pulled. For example <tt>git pull git://dev.omapzoom.org/pub/scm/vikram/omap3.git zoom2_boot</tt>
 * 2) If the patch is sent by email or available in email format, then you can use <tt>git am</tt> and/or <tt>git apply</tt> and/or <tt>GNU patch</tt> commands. Do not forget to use the patch author name when committing patches from somebody else...however you should use your name for the committer.

Check and update the default config
For each 'sync' release, you need to ensure that the default kernel config for the supported platforms is correct. If not you need to change the config. The recommended steps are:


 * 1) Use the default config, e.g. <tt>make omap_zoom2_defconfig</tt>
 * 2) Use kernel config utilities to update the config, e.g. <tt>make menuconfig</tt>, and update the config as needed
 * 3) Replace the default platform config with the new one: <tt>cp .config arch/arm/config/omap_zoom2_defconfig</tt>
 * 4) Commit your changes, <tt>git commit -s</tt>

= Pushing to the remote integration tree =

Pushing your integration branch
At the very beginning, we have created a local copy of the OMAP3 kernel integration tree. So far we have been fetching from remote trees, and merging changes into your local integration tree. It is now time to push these changes on a public tree, and share with others!

First you need to make sure that you are allowed to write to the kernel integration tree, check with the dev.omapzoom.org admin for that. It is just the matter of giving your public SSH identity key to the right person.

Each new sync tree release is always made on the <tt>master</tt> branch on the integration tree. So that we can always consider the integration tree's master branch as the most up-to-date linux kernel for OMAP. It is important to understand what that means:
 * the history of the master branch is always reset to latest linux-omap for each integration release. e.g. there is no common history between each sync tree release
 * it is mandatory to ensure that there is a tag that references the latest commit of the previous integration release before resetting the history. Git will indeed keep in its database only commits that are pointed by a reference (either a head or a tag). As such if no tag is applied then the release content will be lost when the master branch is reset.
 * if the same patch is applied to different integration release, even though the patch content is the same, the commit will be different.

To push your changes, then run

$ git push --tags ssh://xxx@dev.omapzoom.org:29419/pub/scm/integration/kernel-omap3.git +l-o-rc1:master

Where:


 * <tt>xxx</tt> is your username on dev.omapzoom.org
 * <tt>l-o-rc1</tt> is the name of your local branch that you want to push

Note that the local and remote branches can have different names, since the <tt>git push</tt> commands takes the names of both the source and destination branches.

Be aware that with 'write' permissions on the public integration kernel tree, you could damage the public tree... So make sure you understand what you do when running =git push= command, you can for example delete existing branches or destroy history... If you made a mistake and you need to delete a remote branch, you can run =git push ssh://xxx@dev.omapzoom.org:29419/pub/scm/integration/kernel-omap3.git :foo-branch</tt>, where <tt>foo-branch</tt> is the branch to be deleted. This operation is irreversible.