build_afni.py


build_afni.py - compile an AFNI package

  This program is meant to compile AFNI from the git repository.
  It is intended as a quick and convenient way to compile.

* This is NOT intended as a platform for developers.
  This is meant only for compiling, not for making updates to the code.

  The main process (for a new directory) might be something like:

     - create main working tree from the specified -build_root
        - and 'cd' to it
     - prepare git directory tree
        - clone AFNI's git repository under new 'git' directory
        - possibly checkout a branch (master)
        - possibly checkout the most recent tag (AFNI_XX.X.XX)
     - prepare atlases
        - download and extract afni_atlases_dist.tgz package
        - if afni_atlases_dist exists, new atlases will not be pulled
          unless -update_atlases is given
     - prepare src build
        - copy git/afni/src to build_src
        - copy git/afni/doc/README/README.* to build_src
        - copy specified Makefile
        - run build
     - prepare cmake build (optional)
        - run build

  Final comments will be shown about:

     - how to rerun the make build
     - how to rerun the make build test
     - where a command (shell/system) history file is stored
       (hist_commands.txt is generally stored in the -build_root)
     - where the screen output history is stored

examples:

0. basic, start fresh or with updates

Either start from nothing from a clean and updated version.

  build_afni.py -build_root my/build/dir

notes:
  - if there is an existing git tree, pull any updates
  - if there is an existing build_src tree, rename it and start clean

1. simple, but continue where we left off

Use this method to :
  - continue a previously terminated build
  - to rebuild after making updates to the build_src tree
  - to rebuild after installing additional system libraries

  build_afni.py -build_root my/build/dir -clean_root no

notes:
  - if there is an existing git tree, use it (with no updates)
  - if there is an existing build_src directory, keep and use it

2. basic, but specify an existing build package

This implies a Makefile to use for the build.

  build_afni.py -build_root my/build/dir -package linux_centos_7_64

3. use an alternate Makefile, but do not update git repo

build_afni.py -build_root my/build/dir -git_update no \
              -makefile preferred_makefile

4. do not check out any tag

Check out and update to the most recent state of the 'current' branch,
but do not check out any tag.  Also, specify a build package.

  build_afni.py -build_root my/build/dir          \
                -git_branch master -git_tag NONE  \
                -package linux_centos_7_64

5. test the setup, but do not run any make (using -prep_only)

        build_afni.py -build_root my/build/dir -prep_only \
                      -git_update no -makefile preferred_makefile


todo:
  - opts to pass to cmake
  - given a Makefile, will want to detect output package name
  - pick a method for guessing an appropriate Makefile
    Ubuntu vs Fedora vs RedHat vs other vs macos (12+?)

later:
  - sync atlases and build
  - worry about sync to abin

terminal options:

      -help                     : show this help
      -hist                     : show module history
      -show_valid_opts          : list valid options
      -ver                      : show current version

required:

      -build_root BUILD_ROOT    : root directory to use for git and building

other options:

      -abin ABIN                : specify AFNI binary install directory

          default -abin <directory containing afni_proc.py>
          e.g.    -abin $HOME/my_new_abin

          When this option is given, any installation of the compiled binaries
          will be placed into this ABIN directory.  If this option is not
          given, it will be determined by `which afni_proc.py`.

          If this directory does not exist, it will be created upon install.

      -backup_method BACK_METH  : specify how to perform the backup

          default -backup_method rsync
          e.g.    -backup_method mv

          This option is used to specify how a backup of ABIN is made.  It
          should be one of:

                mv      : apply the Unix 'mv' command

                        + Benefit: ABIN is really cleaned, and will not contain
                          any removed files.  This method should be faster.

                rsync   : apply the Unix 'rsync' command
                          (this is the default method)

                        + Benefit: ABIN is preserved during the backup process.
                          Even if the program is terminated while making the
                          backup, ABIN will be maintained.

                        + Benefit: old ABIN files are removed.
                          So old files do not accumulate.
                          If some file or program is no longer built and
                          distributed, it will not linger in the ABIN.

                          After the backup stage, ABIN is emptied before
                          repopulating it with a new install.

                rsync_preserve : use 'rsync', but do not remove old files

                        + Benefit: ABIN is preserved.

                        + Benefit: old ABIN files are never removed.
                          So old files accumulate over time.
                          If some file or program is no longer built and
                          distributed, it will linger in the ABIN.

          See also -do_backup.

      -cc_path PATH/TO/COMPILER : specify the path to a C compiler to use

          e.g.  -cc_path /usr/local/bin/gcc-14
          e.g.  -cc_path NONE

          If a Makefile uses LOCAL_CC_PATH (most do not), one can pass an
          alternative to what is default in the Makefile.

          For example, Makefile.macos_12_x86_64 uses /usr/local/bin/gcc-13.
          This option can be used to override that compiler path as the user
          sees fit, such as with /usr/local/bin/gcc-14 or even /usr/bin/clang.

        * If this option is not used and the default compiler does not exist,
          the program will attempt to find an alternate compiler with a
          different version number.

        * Use NONE to forcibly use the Makefile default, even if it does not
          exist.

      -clean_root yes/no        : specify whether to clean up the build_root

          default -clean_root yes
          e.g.    -clean_root no

          If 'no' is specified, the git directory will not be updated and the
          build_src directory will not be remade.

      -do_backup yes/no         : specify whether to back up abin before install

          default -do_backup yes
          e.g.    -do_backup no

          By default backup will be made whenever a full installation is done
          (of both AFNI binaries and atlases).  The backup (of ABIN, specified
          by -abin) will be placed under the BUILD_ROOT directory (specified
          by -build_root).

          The backup is made by moving the full contents of the abin, so that
          AFNI updates that remove files or programs will indeed remove them.

          If a full install will not be done, a backup will not be made.

          One may use -backup_method to control the command used to make the
          backup.

          See also -backup_method.

      -do_install yes/no       : specify whether to install compiled binaries

          default -do_install yes
          e.g.    -do_install no

          By default, compiled AFNI binaries and atlases will be installed
          into the ABIN directory given by -abin (or else from the $PATH).

          If 'no' is specified, no installation will take place (and no backup
          will be made).

          See also -abin, -do_backup.

      -git_branch BRANCH        : specify a branch to checkout in git

          default -git_branch master
          e.g.    -git_branch some_stupid_branch

          This will checkout and pull the branch.  To build of the most recent
          version of a branch (and not the most recent tag), include:

            -git_tag NONE

          Unless using '-git_update no', the current branch will be updated
          (default master), to make sure any relevant tag will exist.

          Note that precise tags generally refer to a specific branch.  So it
          is easy to specify a branch and a tag that is not actually associated
          with that branch.

          See also -git_tag.

      -git_tag TAG              : specify a tag to checkout in git

          default -git_tag LAST_TAG
          e.g.    -git_tag NONE

          This will lead to 'git checkout TAG', of some sort, depending:

             LAST_TAG   : checkout most recent (annotated) AFNI_XX.X.XX tag.
                          (annotated tags come from official AFNI builds)
             NONE       : do not checkout any specific tag
                          (use this to build from the current branch state)

          By default, the most recent tag is checked out (for the purpose of
          aligning the build with AFNI releases).  To build off of the most
          recent state of a branch, use "-git_tag NONE".

          The LAST_TAG option will generally imply the most recent "official"
          AFNI tag based on the master branch.

      -git_update yes/no        : specify whether to update git repo

          default -git_update yes
          e.g.    -git_update no

          If 'no' is specified, the git/afni/src tree must already exist, and
          nothing will be done to it.  This option cannot be used with
          -git_branch or -git_tag.

      -make_target TARGET       : specify target for make command

          default -make_target itall
          e.g.    -make_target totality
          e.g.    -make_target afni

          When the 'make' command is run under build_src, use the given target.
          Since an individual program make would probably be done directly on
          the command line (rather than using this program), the most typical
          reason to do this might be to save disk space.  Using totality
          (instead of itall) would clean up after the make.

      -makefile MAKEFILE        : specify an alternate Makefile to build from

          default -makefile Makefile.PACKAGE (for the given PACKAGE)
          e.g.    -makefile my.better.makefile

          This option is a mechanism for specifying a Makefile that is not
          (currently) part of the AFNI distribution.

      -package PACKAGE          : specify the desired package to build

          e.g. -package linux_centos_7_64

          The package will imply a Makefile to use, Makefile.PACKAGE.
          It will also be the name of the output binary directory.

      -prep_only                : prepare to but do not run (c)make

          e.g. -prep_only

          This is for testing or for practice.

          Do everything leading up to running cmake or make commands,
          but do not actually run them (make/cmake).  This still requires a
          git tree, but using "-git_update no" is okay.

      -run_cmake yes/no         : choose whether to run a cmake build

          default: -run_cmake no
          e.g.   : -run_cmake yes

          If requested, run a cmake build under the build_cmake directory.

      -run_make yes/no          : choose whether to run a make build

          default: -run_cmake yes
          e.g.   : -run_cmake no

          By default, a make build will be run.  Use this option to specify
          not to.

      -update_atlases yes/no    : update atlases, even if the package exists

          default: -update_atlases yes
          e.g.   : -update_atlases no

          By default, even if the atlases directory exists (afni_atlases_dist),
          it will be updated.  Use this option to avoid a new download.

          If -clean_root is 'no', atlases will not be updated.

      -update_niivue yes/no    : update NiiVue, even if the package exists

          default: -update_niivue yes
          e.g.   : -update_niivue no

          By default, even if NiiVue exists, it will be updated.  Use this
          option to avoid a new download.

          If -clean_root is 'no', NiiVue will not be updated.

      -verb LEVEL               : set the verbosity level (default 1)

          e.g. -verb 2

          Specify how verbose the program should be, from 0=quiet to 4=max.
          As is typical, the default level is 1.

R Reynolds    sometime 2023