# Building the toolset from source

The nosh toolset is known to build, run, and work on FreeBSD 10, PC-BSD 10, NetBSD 10, Debian Linux version 12, and OpenBSD version 5.9. It should similarly build, run, and work on any modern BSD and on any modern Linux flavour. Most expected tweaks in order to make it work on other operating systems have been concentrated in particular areas.

The source is structured as a slashpackage-style package.

It requires redo, `install`, `xmlto`, the host operating system's equivalent of Debian's `build-essential` tools (whatever thay may be), and a POSIX-conformant operating system (with the standard utilities present) to build. (See the Archnosh documentation for the Arch Linux equivalents, for example.)

It builds with the g++ and clang++ compilers. The build system attempts to autodetect the available compiler, as well as various operating-system-dependant features. The way that it autodetects features was in some of Daniel J. Bernstein's softwares: a short test program that references the desired features, and a header that defines a preprocessor macro according to whether the build system can successfully compile and link the test program. (People who absolutely must can override the compiler autodetection with an environment variable.)

It makes use of various `…at()` system calls from POSIX.1:2008, for security and safety. It also makes use of the kqueue mechanism (throughout on BSD, on Linux where library bugs don't make it unusable).

## Building the toolset itself

To just build the toolset from source, without packaging the binaries:

> `package/compile`

This gives you:

- binaries in `command/`, which you can just add to your `PATH` environment variable or symbolically link to;
- manual pages in `manual/`, which you can just add to your `MANPATH` environment variable or symbolically link to;
- examples and various prepared configuration files and service bundles in `config/`, which you will need to copy to apprpriate places; and
- the Guide in `guide/`.

The build process updates files in these directories atomically. It doesn't create part-written executables or other files at their final names. So you can run things straight out of these directories whilst rebuilding.

## Cleaning the build area

To clean the build run

> `package/clean`

or just `rm -r build/`

To clean the build, packaging, and built files run

> `package/distclean`

or just `rm -r build/ command/ manual/ config/ guide/`

## Packaging the binaries

To build installable binary packages on FreeBSD, TrueOS, NetBSD, or OpenBSD run

>     package/bsd/prepare && bsd/rules clean build binary

On FreeBSD and TrueOS this requires pkg version 1.2 or later in order to avoid segmentation faults and other bugs. So ensure that pkg is up to that version in your ports tree.

To build the binary packages on Debian Linux run

>     package/debian/prepare && dpkg-buildpackage -b -uc

## Manual installation

Manual installation is a complex process and not for the faint of heart.

Symbolically linking to stuff in `manual/` and `command/` is better than just putting those two directories on your `PATH` and `MANPATH` as there are a lot of shim commands that might conflict with existing commands on your system. Generally the way to manage such a symbolic link farm is with something like Debian's alternatives system, or a more sophisticated version of the `sp-links` tool from Paul Jarc's sptools toolset, which are both beyond the scope of this Guide.

Separating out all of the stuff in `config/` and copying the necessary parts of it (not all of it being required on every operating system) is perhaps best achieved by building the binary packages and seeing how the package staging areas underneath (on the BSDs) `bsd/nosh-pkgbase/` or (on Debian) `debian/nosh-pkgbase/` are laid out. Likewise, the generated manifests and the pre- and post- installation and deinstallation maintenance scripts in those same subdirectories show what user/group entries to set up in the system account database, what ACLs and permissions to apply to (for example) log directories, and how to do certain special installation/deinstallation steps required for particular services.

Note that the older `package/export` mechanism is no longer available; because there are simply too many optional and potentially conflicting parts for exporting everything as one lump to be feasible.

### Maintenance script generation

The pre- and post- installation and deinstallation maintenance scripts are themselves generated files. They are a combination of:

- a pseudo-declarative list, of things like special file owning users and services that are paired with dedicated logging services, in a `{bsd,debian}/nosh-pkgbase.p` file;

- a shell function library, implementing the pseudo-declarations, in a `{bsd,debian}/{pre,post}-{,de}install.funcs` file; and

- a small amount of glue to load the right shell function library and run the list.

The "plist" mechanisms in pkgsrc and pkg_ng do not have anywhere near enough functionality for the job; but this can be thought of as plists extended to be able to preset/disable services, set ACLs for dedicated rôle accounts, create log directories, and set up non-trivial logging service relationships.

## Porting the toolset to other operating systems

The toolset is packaged as multiple binary packages built from a single source package.

For operating systems outwith the core ones that have binary packages built for them by the author, the source package requires patching. This is in two general areas:

- In `package/stage` patch the operating system's choices of directory layout in the section marked as distributor-patchable stuff.

- In the following files patch to select an appropriate variant of various Desktop Bus configurations, according to whatever choices of non-`PATH` directories and user account names are made by the packages on the operating system.

  - `source/convert/per-user/per-user.conf.do`
  - `source/convert/per-user/gconfd.service.do`
  - `source/convert/per-user/at-spi-dbus-bus.service.do`
  - `source/services/dbus-daemon.service.do`
  - `source/services/dbus-broker.service.do`
  - `source/services/system-wide.conf.do`
  - `source/systemd/service-manager.socket.do`

- In the following files patch to select appropriate pathnames, according to whatever choices are made by the packages on the operating system.

  - `source/convert/rc.conf.do` (in particular `entropy_file`)