Revision History | ||
---|---|---|
Revision 2 | 8 October 2001 | rjh - rhayden@apple.com |
Changed title to "Darwin Committer". | ||
Revision 1 | 1 May 2001 | rb - bbraun@synack.net |
Created. |
Darwin's build system builds new packages within a chroot'ed environment consisting entirely of previously built packages. For example, building a new version of xnu installs all the components needed for building xnu, into a chrooted environment, and then starts building xnu in that chrooted environment. Obviously, this leads to a paradox, since you'll need existing packages before you can build anything with this system. Luckily, I have prepared packages for the entire Darwin 1.2 distribution and have made them available at http://www.darwinfo.org/pub/darwin/built/. You do not need to install these packages. They are used by the build process in their packaged form.
Table of Contents
When building packages, the Darwin build system uses the Tools/buildtools from the Darwin cvs repository. You should check out the latest version and install it before attempting to use the build system. The current system uses a series of perl scripts around the dpkg format, that is why all the packages are .deb. The scripts used are darwin-buildpackage and darwin-buildall. These scripts use the perl modules Dpkg/Package/Builder.pm and Dpkg/Package/Manifest.pm. All these files are included in the buildtools that you should have checked out and installed already.
To build an individual package, you will need buildtools from the cvs repository, and the latest packages needed for building the package you wish to build. That's a bit confusing, so just get the entire directory of packages.
There are two ways to build packages, you can build one from an existing source directory on your local disk, or you can build straight from the cvs repository. I'll cover both of these methods, starting with building from an existing source directory. For these examples it will be assumed that your existing packages are in /src/in and the directory where you wish the new packages to be deposited is /src/out. One important thing to note is that if a required package for building exists in the out directory, it will be used instead of the package in the in directory. This way, you can leave your in directory intact, and use your most recent packages for building.
When building the package, the default build location is /tmp/roots/packagename-version. This is where the required packages will be installed, and the new package will be built. If you wish to change the build location, set the BUILDIT_DIR environment variable to your desired build location. For (t)csh:
setenv BUILDIT_DIR /src/buildit
For Bourne shell:
export BUILDIT_DIR=/src/buildit
For this example, it will be assumed that the source directory you're trying to build is /src/package. To build the package, execute the following as root:
darwin-buildpackage --dir /src/package /src/in /src/out
You have to execute the command as root, since the script will be creating a chrooted environment, installing the necessary tools, building the package, installing it into the chrooted environment, and then packaging it all up.
The first thing you'll have to do for this is to setup your anonymous cvs environment. You'll have to get your anonymous cvs login from Apple, set your CVSROOT environment variable, and login to the cvs server. There are instructions to do that on the Apple anoncvs site, http://www.opensource.apple.com/tools/cvs.
Once you've got your anonymous cvs account and environment setup, you can start building by running the following command as root:
darwin-buildpackage --cvs package-tag /src/in /src/out
The package-tag is the cvs tag for the project you want to build. For example, xnu-3.1.
You can build an entire distribution, or just a subset of it, all at once. This uses the darwin-buildall script, and uses a Manifest file to describe which packages to build. The buildall script only builds from the cvs repository with the cvs tagged versions specified in the Manifest file. The Manifest file can be checked out from the cvs tree, and is located in Darwin/Manifest. This section will first describe the use of the buildall script, and then discuss the format of the Manifest file.
Before running the buildall script, you should setup your anoncvs environment, as discussed earlier. Also, your build location (specified in the BUILDIT_DIR environment variable, defaulting to /tmp/roots) should be a UFS filesystem, otherwise some packages will not build correctly (because of HFS+'s case insensitivity). To run the buildall script execute the following as root:
darwin-buildall Manifest /src/in /src/out
This will check out source from the cvs tree, with the cvs tag specified in the Manifest file, and build it in your build location. The buildall script will progress through the Manifest file starting at the top, and continuing to the next item only after successfully checking out and building the current item.
The Manifest file consistes of one package per line, in the format of:
src is where to get the package from. For the Darwin Manifest in the cvs tree, this is always cvs. The only other valid option is dir, and it will use the next item on the line as the directory to use as the source directory.
project-version is the project to build. If the src is cvs, then this is the cvs tag to check out. If the src is dir, then this is the directory to use for the package source.
target is almost always set to all.
The # character is a comment, so you can comment out different projects that won't build with your current packages.
Although Darwin comes with the dpkg utilities, it has no dpkg database, so it is very difficult to use with Darwin. The easiest way to install .deb's under darwin is to do it by hand. Remember that a .deb is just a bunch of .tar.gz files ar'd together. So to extract the data from a .deb file you can do the following:
ar x file.deb
This will give you several files, but the important one is data.tar.gz. This is the actual data files from the .deb. Then you can cd / and extract the data.tar.gz file. You should use gnutar to extract the file, because of minor behavioral differences between the BSD tar and GNU tar.
If you want to add a package to the build system, there are a couple of things needed. If the package is designed to be built with GNU make (most of them), the process is fairly straight forward. For this example, I'll take the example of xinetd. xinetd is setup to use the GNU autoconf configure script. Here's the series of steps I went through to get xinetd building under the Darwin Build System.
Download the package. The version I'm using is 2.1.8.9pre14, so the package is xinetd-2.1.8.9pre14.tar.gz.
Unpack the package. After untarring the package, I have the directory xinetd-2.1.8.9pre14
Create a directory above the package's directory. Create a directory xinetd and move xinetd-2.1.8.9pre14 into the newly created xinetd directory and rename it xinetd as well:
mkdir xinetd
mv xinetd-2.1.8.9pre14 xinetd/xinetd
Create a dpkg control file. Create the dpkg directory xinetd/dpkg, and create a control file. The control file should be similar to the following:
The Build-Depends tag is a space separated list of packages required to build the package. build-base is a predefined tag that consists of the compiler and most libraries and utilities needed to build most packages.
Create a high level package Makefile. Create a Makefile, xinetd/Makefile, that looks like:
The Extra_Configure_Flags is a list of flags to pass to configure.
Build the package. Run the command to build the system:
sudo darwin-buildpackage --dir xinetd in out
Now, assuming the package properly supports the use of the --srcdir flag to configure, the package will build correctly. Very odd errors can happen when trying to build a package under the Darwin Build System, because it does not build the package in the source directory. Instead it has a separate temporary directory for the intermediate object files.
This section describes how to add a package to the Darwin build system that does not use the GNU Autoconf system to build the project. This section will be rather generic, since a "3rd Party Package" can do just about anything to build its self.
Put the package in a nested directory in mkisofs/mkisofs. This will let the wrapper Makefile and control files go in the top directory, and the actual unmodified source go in the lower directory.
Create a mkisofs/dpkg directory, and a control file within it. The control file should be similar to the one mentioned in the previous GNU Autoconf example.
Create the wrapper Makefile. The Makefile will look similar to this:
This Makefile includes the "Common.make" file, which sets up a bunch of the make rules you'll need, but it does not setup the build or install targets. These are the two targets you'll need to implement in your Makefile for the build system to work correctly.
You will run into problems when trying to get the build system to work. There are a couple of things you'll need to remember. First, you cannot modify the source. Second, you're building in a directory separate from where the source lives. The latter will often cause problems because Makefile variables are setup expecting to be built in the source directory. If it is a simple matter of Makefile variables, you can override them with the Extra_Environment variable in the wrapper Makefile.
Copyright © 2001 by Rob Braun.
This material has been released under and is subject to the terms of the Common Documentation License, v.1.0, the terms of which are hereby incorporated by reference. Please obtain a copy of the License at http://www.opensource.apple.com/cdl/ and read it before using this material. Your use of this material signifies your agreement to the terms of the License.