AMBuild API (2.0)

From AlliedModders Wiki
Revision as of 21:54, 12 November 2013 by BAILOPAN (talk | contribs)
Jump to: navigation, search

AMBuild scripts have access to the following object types:

  • Context: Exposed as the builder, this is the entry point for the API and is known as a configure context.
  • Entry: Represents a node in the dependency graph.
  • Compiler: An abstraction representing a C++ compiler environment.
  • Vendor: An abstraction representing a C++ compiler vendor (GCC, MSVC, Clang, etc).
  • BinaryBuilder: An abstraction for building C++ compilation jobs.

As a general rule, AMBuild uses the following conventions:

  • Methods starting with an upper-case letter are considered public API.
  • Methods starting with a lower-case letter are considered private and should not be used.
  • Properties and attributes ending with an underscore are considered private and should not be used.
  • Spaces are used instead of tabs, and two-space indents are preferred.

Contexts

Contexts are implemented in ambuild2/frontend/base_gen.py. They are the entry point for using AMBuild.

When using paths inside a context, it is important to note how AMBuild recognizes paths.

  • source paths are any paths that are absolute. They must not resolve to a path inside the build folder. Source paths are considered inputs to the build.
  • output paths are any paths that are relative. They are always relative to the build folder. Output paths are generated by the build process.

Attributes

  • compiler - An instance of a Compiler object, or None if DetectCompilers was never called. Calling DetectCompilers will set the compiler field for this and all future contexts. Each context gets a clone of its parent's compiler, so it is safe to modify compilers in inner scripts.
  • parent - The context that loaded the current context.
  • script - The path, relative to sourcePath, of the current build script.
  • sourcePath - The absolute path to the source tree.
  • options - The result of evaluating command-line options from configure.py, via the optparse module.
  • buildPath - The absolute path to the build folder.
  • buildFolder - The working directory of jobs in this context, relative to buildPath.
  • localFolder - The Entry for buildFolder; None for the root of the build.
  • currentSourcePath - The source folder that the current build script is in.

Methods

  • SetBuildFolder(folder) - Sets the working directory of jobs in this context, relative to buildPath.
    • folder - A string representing the folder path. '.' and './' are allowed.
    • Returns None.
  • DetectCompilers() - Detects C and C++ compilers and raises an exception if neither are available or they do not match. Should only be called once.
    • Returns a Compiler object that is also accessible via the compiler attribute.
  • RunScript(files, vars={}) - Runs one additional build script.
    • file - A string containing a file path, relative to the current script's path.
    • vars - An optional dictionary of global variables to set in each child build script. The dictionary is merged with the global variables passed into our current script. Variables with the same name are overridden by the new dictionary.
    • Returns the global variable rvalue if set in the child script; otherwise, returns None.
  • RunBuildScripts(files, vars={}) - Runs additional build scripts.
    • files - An iterable containing a list of file paths relative to path of the current build script, or a string containing such a path.
    • vars - An optional dictionary of global variables to set in each child build script. The dictionary is merged with the global variables passed into our current script. Variables with the same name are overridden by the new dictionary.
    • Returns None.
  • Add(taskbuilder) - Some jobs are too complex to use a single API call, and instead provide objects to assist in creation. These objects are finalized into the dependency graph with this function. Currently, the only complex jobs built-in are C/C++ compilation jobs.
    • taskbuilder - The job builder instance.
    • Returns a value based on the taskbuilder. For example, C++ objects return a 'CppNode' described under the Compiler section.
  • AddFolder(folder) - Ensures that a folder is created when performing a build. The folder is created relative to the context's local build folder.
    • folder - A relative path specifying the folder. Folder chains can be created all at once; i.e. 'a/b/c' is a valid target even if 'a' or 'a/b' do not exist.
    • Returns an Entry instance describing the folder creation node.
  • AddSymlink(source, output_path) - Adds a job to the build that will perform a symlink. On systems where symlinks are not available, it is implemented as a copy.
  • AddCopy(source, output_path) - Adds a job to the build that will perform a file copy.
    • source - Either a string containing a source file path, or a source node, or an output node, representing the file that will be the source of the operation.
    • output_path - One of the following:
      • A string path ending in a path separator, or '.', specifying the folder to copy or symlink the file to. It is relative to the context's local build folder.
      • A string path ending in a filename, representing the destination file of the operation. It is relative to the context's local build folder.
      • A folder node created via AddFolder(), representing the folder to copy or symlink the file to. In this case, the folder node's path is taken as-is and is not relative to the local build folder.
    • See AddCommand for return values.
  • AddCommand(argv, inputs, argv, outputs, folder?) - Adds a custom command that will be executed manually. The working directory of the command is the context's local build folder. As created, the command has no dependencies. If it has source dependencies they can be specified via AddDependency.
    • inputs - An iterable containing source file paths and/or Entry output-file nodes that are incoming dependencies.
    • argv - The argument vector that will be passed to subprocess.Popen. argv[0] should be the executable.
    • outputs - An iterable containing files that are outputs of this command. Each file must be a relative path from the context's local build folder.
    • folder - The working directory for the command. By default, this is buildFolder. It can be None to specify the root of the build. Otherwise, it must be an Entry from calling AddFolder or reading localFolder.
    • Returns a 2-tuple, containing:
      • An Entry instance representing the node for this command in the dependency graph.
      • A list of Entry instances, each instance corresponding to one of the output file paths specified.
  • AddConfigureFile(path) - Adds a source path that will trigger automatic reconfiguring if the file changes. This is useful for files that are conceptually part of a build script, but are not actually loaded as a build script.
    • path - A source path.

Entry

Entry objects are considered mostly opaque. However, all frontends must define at least these attributes:

  • path - A file system path that uniquely represents nodes that are present in the filesystem, such as source files, output files, or folders.

Compiler

Compiler objects encapsulate information about invoking the C or C++ compiler. Most of its attributes are lists of options, so it is best to use += to extend these lists, to avoid replacing previously set options.

Whenever options come in pairs - for example, C/C++ flags versus C++-only flags, C++ flags will automatically include all C flags during compilation time.

Attributes

  • includes - List of C and C++ include paths
  • cxxincludes - List of C++ include paths.
  • cflags - List of C and C++ compiler flags.
  • cxxflags - List of C++ compiler flags.
  • defines - List of C and C++ #defines, in the form of 'KEY' or 'KEY=VALUE'
  • linkflags - Link flags (see below).
  • postlink - Array of objects to link, added to the linker flags after linkflags. See below.
  • sourcedeps - An array of output nodes which should be weak dependencies on each source compilation node.
  • cc - A Vendor object describing the C compiler.
  • cxx - A Vendor object describing the C++ compiler.

Entries to linkflags and postlink can be:

  • A string representing a linker flag.
  • An absolute file path representing an input file to the linker (it will be included as a dependency automatically).
  • A Dep object. Dep objects are useful when precise control is needed over what text is given to the linker in order to link in a file. Essentially, they let you customize the link flag while still including a dependency. They also allow lazy computation of dependencies, since sometimes extra steps must be generated before linking to an object. Dep objects have two attributes:
    • text, the text that will be passed to the linker when constructing its argument list.
    • node, an object which tells AMBuild how to build a dependency for the linker flag. It can be:
      • An Entry or list of Entry objects representing the output files of a command, or
      • A function which returns the above, and has the signature (builder, binary), receiving a Context object and a BinaryBuilder object.
  • Note: AMBuild does not currently support automatic dependency generation for -L style linking.

For example, to generate a linker invocation like "g++ main.o tier1.so -o main", where tier1.so is a generated file, you could do:

binary.postlink += [binary.Dep('tier1.so', tier1_so_entry)]

If this requires symlinking tier1.so to be in the local folder, you can get more complex, such as:

def make_linker_dep(compiler, name, entry):
  def lazy_dep(builder, binary):
    cmd, (output,) = builder.AddSymlink(entry, '.')
    return output
  return compiler.Dep(name, lazy_dep)

Methods

  • Dep(text, node) - Creates a Dep object instance (see above for more details).
  • Program(name) - Creates a new BinaryBuilder instance, with a copy of the compiler settings. The builder is configured to generate an executable (.exe is automatically appended on Windows).
  • Library(name) - Creates a new BinaryBuilder instance, with a copy of the compiler settings. The builder is configured to generate a shared library. .so, .dylib, or .dll is automatically appended depending on the platform. Nothing is ever prepended to the name.
  • StaticLibrary(name) - Creates a new BinaryBuilder instance, with a copy of the compiler settings. The builder is configured to generate a static library. .a or .lib is automatically appended depending on the platform. Nothing is ever prepended to the name.

Vendor

Vendor objects describe basic information about a C or C++ compiler. They have the following supported attributes:

  • name - A short-hand string to identify the compiler. Currently, this is one of:
    • "msvc" - Microsoft Visual C/C++, invoked via cl
    • "gcc" - The GNU C/C++ Compiler
    • "clang" - The Clang C/C++ Compiler
    • "icc" - The Intel C/C++ Compiler
  • version - An arbitrary version string.
  • behavior - A short-hand string identifying whether the compiler behaves like GCC ("gcc") or MSVC ("msvc").

In addition, if behavior is "gcc", the following attributes are available:

  • majorVersion - The major version number of the compiler (for example, 3 in Clang 3.0.2).
  • minorVersion - The minor version number of the compiler (for exmaple, 0 in Clang 3.0.2).

BinaryBuilder

BinaryBuilder assists in creating C/C++ compilation tasks. Once you've set all the information needed, they are integrated into the dependency graph by using builder.Add().

Attributes

  • compiler - A full copy of the compiler settings used when instantiating this BinaryBuilder. Modifying this compiler will not modify the original builder.compiler.
  • sources - An (initially empty) list of C/C++ source file paths. They can be absolute paths, or paths relative to currentSourcePath.
  • localFolder - The name of the folder this binary will be generated in, relative to the buildFolder of the context that adds the tasks.

Methods

  • Dep(text, node) - A wrapper for compiler.Dep.