We use Perforce at my shop, and have a semi-unique system due to the way our product (embedded software in lots of hardware) is. We’ve got a few configurations, all similar, all to different customers, and the customers are the type that want to know what the changes are if they get a new version, and don’t want anything too different than the last one, even if it’s “better”.
We rely on branching to let us do our development for a specific project on a “development” branch, maintain a “release” branch for each project, and have a “mainline” where we try to collect all the latest things from every single project, so that when we start a new project, we have the sum total of all the newest stuff that we’ve done.
This relies on good developers communicating, as well as making sure that they’re always adding features. Feature B gets added to module 1, so module 1 has Features A and B, rather than module 1 being changed to be B not A.
Our revision graphs in Perforce are truly amazing things to behold, but it works well, and we’ve support numerous products at varying states of release on different hardware with a small number of developers with a minumum of chaos.