Arnd Bergmann <[email protected]>
One version of the ST-Ericsson BSP can be found at http://git.linaro.org/gitweb?p=bsp/st-ericsson/linux-2.6.34-ux500.git This currently includes only the kernel for a fixed release for the u8500 and u5500 SoCs. The work that is going into the upstream kernel is related but does not directly correspond to the files in there
The git tree contains a series of about 750 (at time of writing) patches on top of the Linux-2.6.34 kernel. The largest patch by far is the first one, which adds most of the code to the kernel tree, the patches on top are a most unordered set of additional drivers, bug fixes, cleanups and backports from upstream and from android sources.
The actual platform code is initially added to the arch/arm/mach-u8500 directory and subsequently moved to arch/arm/mach-ux500, which is the corresponding directory in the upstream kernel. The BSP in total consists of over 60% device driver code however. A rough impression can be gained from git:
git diff v2.6.34 --dirstat=1 2.0% Documentation/DocBook/ 3.9% arch/arm/configs/ 7.1% arch/arm/mach-ux500/include/mach/ 7.4% arch/arm/mach-ux500/ 1.4% drivers/input/ 4.5% drivers/media/radio/CG2900/ 5.6% drivers/mfd/ste_conn/ 1.2% drivers/mfd/ 2.8% drivers/misc/audio_io_dev/ 1.2% drivers/misc/hsi/hsi-legacy/ 1.3% drivers/misc/hsi/ 1.4% drivers/misc/i2s/ 2.1% drivers/misc/shrm/ 3.3% drivers/misc/ 1.5% drivers/net/caif/ 1.4% drivers/power/ 1.8% drivers/spi/ 5.2% drivers/video/av8100/ 6.3% drivers/video/b2r2/ 6.9% drivers/video/mcde/ 5.4% drivers/ 3.3% firmware/ 2.8% include/linux/ 1.5% include/ 3.1% net/caif/ 1.8% sound/arm/ 1.0% sound/soc/codecs/ 9.7% sound/
The ux500 platform
Much of the platform code is derived from the ARM realview platform code, which makes sense since the hardware also seems to be based on similar licensed function blocks. The way that the BSP kernel is maintained makes it relatively hard to compare with upstream kernels. Platform code that is only supported in the BSP and not yet in 2.6.36 includes:
- U5500/U8500 simulator platform
- "mcde" platform
- "STM" DMA
- Display drivers
- cpu frequency scaling
- cpu idle
- "MBOX" driver
- some time sources
The upstream kernel maintainer, Linus Walleij, is cleaning up parts of the platform at a time, and integrating them, while work on the private repository continues in parallel.
The "Communication CPU to Application CPU Interface" (CAIF) network protocol was recently merged into 2.6.36 and has its roots in the ST-Ericsson BSP. There are still significant portions of CAIF that did not get merged and are present in the BSP:
git diff --stat v2.6.34 drivers/net/caif/ net/caif/ include/net/caif/ | tail -n1 55 files changed, 14513 insertions(+), 0 deletions(-) git diff --stat v2.6.36-rc5 drivers/net/caif/ net/caif/ include/net/caif/ | tail -n1 50 files changed, 6825 insertions(+), 790 deletions(-)
It is not clear what will happen to them, some parts may well remain out of tree, while others probably need to get merged.
A large number of device drivers of varying quality is distributed with the BSP. A very brief review of all the drivers reveals:
- Ambient light sensor driver
- This provides a read-only sysfs interface to ambient light data.
- Discussion about the interface will be necessary, apparently some people feel this should be an input driver.
- Accelerated crypto driver for SHA1/SHA256
- looks non-controversial, but requires controversial DMA interface
- GPIO drivers for GPIO expanders (stmpe1601, stmpe2401, tc35892)
- probably non-controversial
- HWMON drivers (lsm303dlh_a, lsm303dlh_m)
- input drivers for several keypads (ske, tc35893, u8500-kpd)
- probably non-controversial
- input driver for vibra using force-feedback commands
- driver looks clean, no idea if the concept is right.
- input driver for touchscreen
- clean but rather large
- LED drivers (ab8500, lp5521)
- ab8500 looks clean enough, but probably needs to be restructured to use a proper bus
- lp5521 uses a nonstandard user interface, probably can't go upstream like this
- CG2900 radio driver
- very large driver, has issues
- multi-function drivers (ab3550, ab5500, abx500)
- mostly ok, needs review
- ste_conn multi-function driver
- not ok, might need a rewrite from scratch
- ab8500 multi-function driver
- needs rewrite to an actual multi-function driver
- audio_io_dev driver
- needs rewrite to an ALSA sound driver
- HSI/MSW subsystem
- unclear what this actually does
- might get turned into a tty line discipline
- "legacy HSI" driver even worse
- needs cleanup
- hwmem device driver
- probably needs to die a quick death
- i2s subsystem
- seems reasonable to have, but needs to coexist with existing ad-hoc i2s code
- infrared remote control driver
- wrong in many ways, needs to be rewritten as input or lirc driver
- android pmem driver
- doesn't belong here
- shared memory modem driver
- homegrown API, need to find a more standard API and rewrite
- u8500 MMC driver
- mostly ok, could use a little cleanup before merge
- ab8500 battery management driver
- looks huge
- will need changes from ab8500 mfd driver rewrite
- ab8500 regulator driver
- will need changes from ab8500 mfd driver rewrite, otherwise ok
- spi drivers (msp, spi023, ssp)
- probably uncontroversial
- trusted execution environment (TEE/Trustzone) driver
- small driver, but unacceptable user interface
- stm musb driver
- ok in principle, needs a bit of work
- av8100 "video" driver
- just an display output (hdmi) driver, not actually a frame buffer
- has multiple issues, probably fixable
- b2r2 accelerated frame buffer driver
- mcde frame buffer "subsystem"
- basic frame buffer driver ok
- should not be a subsystem or a bus
- firmware files
- don't belong into the kernel tree
- blkdev partition driver
- can be replaced by a small shell script in initrd
- ab8500 sound codec
- not coding style conforming, did not look
- ab3550 ALSA codec driver
- probably ok
- ux500 ALSA SOC drivers
- looks uncontroversial
Recommendations and best practices
As seen from the repository contents, a number of things could be changed to improve interaction with users, upstream developers and Linaro.
Having all those different drivers and other things maintained in a single tree is not helpful for long-term maintainance. The number of patches alone makes it imposssible to review what has gone upstream or what is even headed that way. In practice, none of the patches will directly get merged anywhere but rather need to be changed in some way, which then disrupts the history for the entire tree.
A topic branch keeps a separate history for each component, which makes it much easier to review just that one component, or to decide when to do a rebase to a newer upstream release, a merge from upstream changes, folding bug fixes together or even removing the branch entirely when its contents get merged upstream.
A reasonable set of branches for this particular BSP could be
- mach-ux500 platform changes (non-driver)
- uncontroversial drivers on their way upstream
- ab8500 framework and drivers using it
- video drivers
- drivers owned by other parties like google
- other drivers that need a lot of work (possibly one tree per driver)
Each of these branches can be based on an arbitrary kernel release, as long as it cleanly merges with the current head. On a regular basis (e.g. once per day, or once per week), all branches pulled into a single tree for an octopus merge. Developers working on one of the branches have the choice to test their code either with none of the other branches applied, or to work on the combined tree but then only commit to their own branch.
In order to create a topic branch from the existing history, git-format-patch origin/master path/to/subsystem can be use for generating a set of patches that subsequently gets applied to a fresh branch using git-am.
Topic branches themselves can be merged from more specific branches like one branch per developer or be maintained by multiple people together.
The master branch can be either regenerated from scratch every time like the linaro arm-next tree, or it can keep the entire history as long as the topic branches never get rebased.
The platform branch
The code in arch/arm/mach-ux500 suffers particularly from lack of maintenance. With the merge to 2.6.34, all history was lost and the contents of the upstream kernel that were already merged got replaced with a different copy that holds an older but more complete version. There is probably no sensible way to turn this into a meaningful rebaseable history again. Going forward, a fresh start on a more recent base version (e.g. 2.6.36-rc5 at time of writing) would be a sensible way to start a topic branch.
Using git add -i, it is possible to add parts of the contents of a directory, and even single hunks of a patch to one commit, in order to split different kinds of contents of the directory into a reasonable changeset history.
A particular nuisance is the devices.c file, which contains the definitions of all devices and has to match the version in the device driver. This will continue to be a problem, but may improve as the platform gets converted to use a device tree source (tds) file to describe the hardware.
Staying on the latest kernel version
The tree is trailing the upstream version by almost two releases at time of writing, which causes a lot of churn when code gets partly merged. The motivation for remaining on an outdated kernel is usually stability of products based on it. The only way to avoid the extra work caused by this is to split the stable release from the development release and always keep the development release up-to-date with the latest upstream snapshot. Obviously, the stable version needs to get bug fixes but it should never see any new development in order to avoid duplication of work.
Slow-moving topic branches can remain on the stable version and get merged into the master.
When a new version gets chosen for the next stable tree, the old stable tree should be quickly retired and made read-only to preserve the version history. When the development takes place on the upstream version, there is never a need to forward-port significant amounts of code and transition to a new stable version can happen very quickly.
The upstream drivers/staging infrastructure is there for device driver code that is not yet fully acceptable in the mainline release but has active users a compliant license (GPLv2 compatible) for getting merged. This is true for most of the device drivers in this BSP, and it would be helpful to use drivers/staging as a vehicle to make the upstream (and Linaro) kernel work much better out of the box on upstream kernels.
Moving a driver into staging means giving up official maintainership until the code becomes ready to move to its final destination, but at the same time adds more responsibility to actually fix the outstanding issues. Every staging driver has a TODO file associated with it that lists the necessary changes before the driver can graduate out of staging. This implies that no other version of the driver should be maintained outside of the staging area in a private tree and all changes go directly to the staging maintainer (Greg Kroah-Hartman). Maintaining separate changes elsewhere obviously defeats the purpose of drivers/staging.
If work on a staging driver stalls, it will get removed again at a later point, which is the only way to put pressure on the developers to actually fix the issues in the TODO file.
Graduating out of staging by fixing the issues in the TODO file is just one option however, the more common option for hopeless cases is to work on a rewrite in parallel and remove the staging driver once the replacement gets merged.
Great article on the kernel development process (http://lwn.net/Articles/269120/) Will help better understand some of the concepts Arnd outlined above
Explanation of the kernel-staging tree (http://lwn.net/Articles/285594/). Good short read.
BSP/ST-Ericsson (last modified 2011-04-04 17:09:00)