The short version: I've replaced the Imake build system in ctwm with a CMake structure. Comments on the concept in general or the implementation in specific are solicited. This is the first time I've tried seriously using cmake, so I'm in no position to claim it's done in the best possible way. But it works for me, and looks OK in reading.
Branch has been pushed up to LP. Branch at 'lp:~fullermd/ctwm/cmake', URL <https://code.launchpad.net/~fullermd/ctwm/cmake>. Tarball <http://bazaar.launchpad.net/~fullermd/ctwm/cmake/tarball/343> if that's your preferred (at least as of the current head rev; watch out for it changing). README describes more details of invoking it, but for most systems the Makefile in the root should do it all behind your back just fine; just run 'make'. See how it does it and/or README for more details if you need to (or want to) experiment with using it directly. Builds should wind up largely with the defaults currently extant, with the exception that USE_GNU_REGEX is enabled by default. It doesn't actually have anything to do with GNU; it just uses regex functions from libc. If we find that we're dealing with a ton of systems that don't have a regexp implementation in libc, well, we'll worry about that then. Other than that, please test and comment! If it does well, we wanna land it, and if it doesn't, we'll need to come up with a backup plan. --------------------------------- The long version: Why Imake ctwm uses imake because twm used imake. And twm used imake because, well, everything X used imake. And imake does a lot of things well in practice, and an even larger set in theory. In particular, it knows (practically by definition) everything about how X is installed on the local system, and how to link in all the needed pieces. It also knows, because it's build with that knowledge, where the compiler and linker are and how to invoke them. And it knows, because the sysadmin sets local configuration, what other things are available and how to get at them. Why not Imake The practice, mostly doesn't work that well. It still knows X, but it may or may not know the local compiler with the rise of binary packages, and if sysadmins regularly made local configuration to it in the 1980's, they sure as heck don't know. And it's not even necessarily that reliable on X anymore, since X itself no longer uses it. What we need We don't per se _need_ a Makefile builder. I know perfectly well how to write Makefiles, and so do plenty of other people around. But we do need something that sets things up cross-platform. That knows how to interact with different make's[0] and different compilers and linkers. That can handle a configuration role, of en/disabling capabilities, finding libraries and includes, etc. That can, well, not make us HAVE to deal with some of the messy bits of Makefile writing. So we might as well go whole-hog. What are our choices? I discarded right off the class of reimplemented build systems, like scons and rake and jam and such. We want something that just builds a standard buildchain. There are 3 major options I'm aware of: GNU autotools, qmake, and cmake. I'm passingly aware of some others (like gyp), but I didn't give them more than a passing glance. autotools I think this can best be summed up as "just, no". It's the way the rest of X went when they discarded imake, but nothing I've ever seen from it as either a user or a dev makes me want to get any closer. The few times I've had to deal with autotools intimately have ranked solidly among my least pleasant programming experiences. The only significant plus is that, on the end-user system, they don't require anything but a Bourne shell. qmake I didn't investigate this too deeply. It's built for Qt, but isn't strictly Qt specific; it can certainly be used for other things. But it usually isn't, and even a lot of Qt stuff seems to have moved to CMake instead. CMake Well represented in the free software world now, it's got maturity and momentum. In my readings of docs and existing files out there, it seems relatively unpainful to work with, so I chose to run with it. My experience porting ctwm to it has been fairly pleasant; the docs aren't always great, but I could figure things out, and it seems fairly easy to reason about. Cmake plus/minus/notes CMake is standalone, and doesn't require any dependencies beyond itself. On the other hand, it is a large C++ program; some old systems might not have a compiler competent to handle it. They do seem to cover the recent *nixen well, plus Mac and Win, and there is evidence of _some_ level of VMS support (though http://public.kitware.com/Bug/view.php?id=3974 suggests it's not complete). It does require that you have cmake around to build ctwm. And if you have to build it to get it around, it takes a lot longer to build than ctwm does (but hey, we require X, which also takes a long time). We no longer have to copy/edit an Imakefile.local to en/disable things; it can all be done on the cmake command line like autoconf and friends do. I haven't added specific hooks for setting odd library/include dirs, though you can via the generic cmake params like CMAKE_SYSTEM_INCLUDE_PATH etc. The build happens out of tree; all the intermediate and final generated files wind up under build/. So rm -rf build/* cleans up everything. Actual command lines for things like the compiler runs can be made visible via 'make VERBOSE=1' Full stack through install is easy to test with DESTDIR just like before. e.g., "make DESTDIR=/tmp/ctwm allclean all install" will run you from pristine through installed in /tmp/ctwm/$PREFIX. CMake is common enough that various OS packaging systems probably already have recipes that make it easy to package for them. Imake is getting toward unloved enough that things might be getting trickier. There's probably more or different things that can be done. I have it erroring out if e.g. libjpeg is enabled, but not found. It's possibly we'd want it more automated like "use if available, otherwise don't"; I chose to do it this way because I like more immediate feedback if things aren't as expected. Similarly, a possible future step would be splitting things up the source tree a little more, rather than having everything (except the pile of XPM's anyway) in the root of the tree. Such things are intentionally not yet investigated; one thing at a time. Random cmake refs/tabs I've kept open through the process: (in no order, just a tabdump) <http://www.cmake.org/cmake/help/v2.8.12/cmake.html> <http://www.cmake.org/Wiki/CMake> <http://www.cmake.org/Wiki/CMake_FAQ> <http://rachid.koucha.free.fr/tech_corner/cmake_manual.html> [0] Or other build systems completely. It will build configs for various IDE's (on Mac frex may be interesting for us) and can do so for some other build systems too. For instance, it can build ninja control files; tested lightly and works fine here, so you can go that way if all those dozens of microseconds make wastes ordering dependencies are messing with your build times. -- Matthew Fuller (MF4839) | [email protected] Systems/Network Administrator | http://www.over-yonder.net/~fullermd/ On the Internet, nobody can hear you scream.
