Understanding rebuilds
----------------------

As packages are processed in order (based off of detected dependencies, if any),
each package will go through their respective stages: fetching, extraction,
patching, configuration, building and installation. While a package may not take
advantage of each stage, the releng-tool will step through each stage to track
its progress. Due to the vast number of ways a package can be defined, the
ability for releng-tool to determine when a previously executed stage is "stale"
is non-trivial. Instead of attempting to manage "stale" package stages,
releng-tool leaves the responsibility to the builder to deal with these
scenarios. This idea is important for developers to understand how it is
possible to perform rebuilds of packages to avoid a full rebuild of the entire
project.

Consider the following example: a project has three packages ``module-a``,
``module-b`` and ``module-c`` which are C++-based. For this example, project
``module-b`` depends on ``module-a`` and project ``module-c`` depends on
``module-b``; therefore, releng-tool will process packages in the order
``module-a -> module-b -> module-c``. In this example, the project is building
until a failure is detected in package ``module-c``:

.. code-block:: shell-session

   $ releng-tool
   [module-a built]
   [module-b built]
   [error in module-c]

A developer notices that it is due to an issue found in ``module-b``; however,
instead of attempting to redo everything from a fresh start, the developer
wishes to test the process by manually making the change in ``module-b`` to
complete the build process. The developer makes the change, re-invokes
``releng-tool`` but still notices the build error occurs:

.. code-block:: shell-session

   $ releng-tool
   [error in module-c]

The issue here is that since ``module-b`` has already been processed, none of
the interim changes made will be available for ``module-c`` to use. To take
advantage of the new implementation in ``module-b``, the builder can signal for
the updated package to be rebuilt:

.. code-block:: shell-session

   $ releng-tool module-b-rebuild
   [module-b rebuilt]

With ``module-b`` in a more desired state, a re-invoke of ``releng-tool`` could
allow ``module-c`` to be built.

.. code-block:: shell-session

   $ releng-tool
   [module-c built]

This is a very simple example to consider, and attempts to rebuild can vary
based on the packages, changes and languages used.
