Hi!
I am soon starting to maintain a line of products containing variants of the same embedded software. Since I've been playing with git for one year and appreciate it very much, I'm likely to use it for source control.
There are several options I can see for maintaining the variants of the firmware, but none pleases me too much. What are the best practices you apply for your own work?
Alternatives I can think of:
defines. Pre-processing. Pros: everything is always present in the source code, it is harder to miss the update of one of the products. Cons: harder to read. It might be ok while we have only two variants, when it becomes four or more it will be a pain. Also, it seems harder to apply the DRY principle (Don't Repeat Yourself).
one branch per product variant. When changes that apply to all products are included, the change must be merged to the other products. Cons: if a commit contains both changes for all products and changes for the specific variant, there will be trouble. Of course, you can make sure that a commit contains only one kind of change: this-product-changes, or the-whole-family-changes. But try to force that on a team?? Plus then merging wouldn't work, we should be cherry-picking instead. Right?
a core repository as a submodule. Make all files that contain core functionality a repository on its own. All products contain a version of the core repository as a sub-module. Cons: I can't see that there wouldn't eventually be variants of the core submodule. Then we're in trouble again, and then we'd use defines or something bad again. A core repository with branches? Then we're back to the previous alternative: a change that applies to all branches must be merged but merging includes also the product specific stuff.
create a repository per module. For example a repository for a display driver, another one for the power management hardware, yet another for the user input interface, ... Pros: good modularity. Make a new product by just picking up the modules you need as submodules! All submodules might have branches, if for example a variant uses the hardware in a different way. Cons: Lots and lots of modules, each keeping track of a couple of files (an include file and a source file). A hassle. Someone makes an important update in some module? Then someone needs to include the change in the other branches of this module, if appropriate. Then someone must also update the submodule in every product repository. Quite some work, and we kindof lose the snapshot side of git.
How do you do it, and how has it been working? Or how would you do it?
I have a feeling that I should get experienced with cherry picking.