Friday, August 15, 2014

Setting up a new project with a new build system.

Hi.

This is my first post in what I hope to be a series of tutorials on setting up a build system for a new project. Note that I am writing this with basic knowledge of how Makefiles work, some experience using Chromium build system, and not much more. As such, I'm not claiming that these series will be a correct comprehensive guide to how to do things. This will just be a log of what I have personally done and what worked for me.

This post is simply an introduction to what I have and what I want to accomplish.

Currently, I'm a Chromium developer, so I use the Chromium build system. This means depot_tools (gclient in particular), ninja instead of make, and gyp/gn files as files that specify targets and source files. From what I have seen, these tools are fairly powerful. The files they generate are readable, the code compiles well :)

Two things I like about it in particular:

  1. Separate binaries for unittests. These are specified as separate targets and produce separate executables that, when run, execute specified tests. Chromium uses Google Test libraries, which is what I plan to use as well.
  2. Ability to compile for different platforms. The magical thing here is that the same build system is used for all operating systems (expect for maybe iOS). This means that as a contributor, I don't need to worry about hacking some makefile in multiple places to ensure that everything works for all platforms. I think the magic is in the gyp or gn files.
Those two things among others is the reason I decided to convert my toy projects from Makefiles to gclient/gn build system (By the way, if there's an official name for the build system that I can use, please let me know).

As a developer, what I do best is programming. For me, this means writing C++ code, ensuring it compiles and links into an executable, and produces results that I want. However, one thing always bugged me about starting new projects: setting up the build system. I am currently working on some toy projects with no other goal but learning more of C++11 and I'm facing the same challenge again.

I have my base project checked in to git. It has some external library dependencies, such as googletest, zlib, libpng, etc. I currently just have those checked in to the code as well, under "third_party" directory. Additionally, I have a bunch of Makefiles that build the main project, as well as static libraries from third_party. The makefiles also link things correctly and are even able to run some tests. However, it's all a big unmaintainable mess.

In particular, every time I have to edit a Makefile, I immediately get a headache, struggle for half an hour to remember why I wrote the Makefile the way I did, then hack something together, test it, inevitably break some other target, and commit. Later, I go back and fix whatever I broke hoping I don't break more things.

So, I decided to document my exploration into something better. I want to be able to explain to a person looking at my code and build system for the first time what is going on. Moreover, I want to understand every line of what I write in my build system and the reason for me writing it. I don't want to do any more hacks.

As a disclaimer, I fully recognize that there are people out there whose Make-foo is awesome and they can do magic. I'm not one of these people.

Here are some notations that I will use:

  • I will use example.com as a host where my git repos are hosted.
  • I will try my best to document exactly what I type, even if it's incorrect (of course, I will explain the thing that worked later)
  • I will try to come up with more bullet points if I decide to use bullet points.
  • Apparently, I will also have to learn HTML in order to use this blogger properly.

- vmpstr

No comments:

Post a Comment