Overview

brahms_execution is a Matlab object that corresponds to a BRAHMS Execution File. It is constructed using the syntax exe = brahms_execution, and then the object can be modified. It is passed to brahms for writing to file automatically, or can be written to file explicitly using the serialize() call.

Interface

Properties

Like the fields of a structure in Matlab (see the Example below).

name
This parameter, along with workingDirectory is used to name the Execution File, System File, and Report File (if these filenames are not specified explicitly). If absent, "unnamed" is assumed.
systemFile, executionFile, reportFile, consoleFile
These fields allow to specify explicitly the names of all files written on calling brahms, overriding the automatic setting. The first two are also written into the Execution File.
title, workingDirectory, executionStop, seed
These fields give direct one-to-one access to the corresponding fields (note case may vary) in the Execution File. executionStop can also be reached through the synonym stop.
precision, toggle, encapsulated, all
Gives access to the attributes of the <Logs> tag of the Execution File.
voices
(READ ONLY) Returns the number of Voices in the Execution (set addresses to write this value).
addresses
Gives access to the <Voices> tag of the Execution File. Syntaxes accepted are: exe.addresses = {comms N}, with comms the communications protocol ('sockets' or 'mpi') and N the number of Voices (this sets up a Babble); exe.addresses = {ip1, ip2, ...} with each ip<n> a string holding an IP address (this sets up a Concerto Execution on remote machines). See example below.
affinity
Gives access to the <Affinity> tag of the Execution File. Set this to a single cell array, with each cell representing a <Group>. Each <Group> cell should itself be a cell array containing a list of strings, representing the <Identifier> tags within the <Group> tag. Exactly one number can be included in a group cell, in which case it will be interpreted as an explicit assignment of that Group to a specific Voice (this is useful if your hardware is not symmetric). See example below.
execPars
Any Execution Parameter can be set as a sub-field of this field, for example exe.execPars.MultiThread = false. Any parameter that has been set can be read back in a similar way.
launch
The Launch Line is used to launch the BRAHMS executable when the time comes. See below for details.

Methods

Note that the old usage of this function of the form exe = exe.log(..., key, value, ...) is now replaced by exe = exe.log(..., {key, value}, ...).

exe = exe.log(name, ...)
Request logging of one or more output Ports or Processes by using this function. The first argument "name" should be the SystemML Absolute Identifier of the output Port, Process or Subsystem you want logged. Additional arguments should be flags or key-value pairs in a two-element cell. Key-value pairs may include {'precision', <number>} and {'toggle', [<time> <time> ...]}. Flags may include 'encapsulated' ('encap'), 'unencapsulated' ('unencap'), and 'norecurse'. By default, "Recurse" is set on the Log, so any descendants of the specified object are also logged; to turn this off, pass the flag 'norecurse'.

Launch Line

To allow total flexibility in launching BRAHMS through the Matlab Bindings on any hardware or software configuration, no attempt is made to cover all bases, and we use instead a "Launch Line" which is invoked through the system() call, and which can be chosen by the user. The Launch Line system is intended to allow customisation of a launch to your local context, and is not needed for typical simulations. It becomes useful when you have hardware to interact with, or esoteric deployment situations. The more esoteric, the more of this section you'll want to read.

For instance, a common requirement is to launch different voices on different machines. If running in Sockets mode, their IP address is already stored, so you can use a Launch Line that uses ssh and the IP to start the BRAHMS voice on a remote machine. Whatever form the launch line takes, certain tokens are replaced by something appropriate before it is used, as follows.

$(MATLAB)
Either "matlab " (nested mode), or "" (parallel mode) - the BRAHMS wrapper script behaves slightly differently when called with the "matlab" argument on some platforms.
$(EXECFILE)
The full path to the Execution File.
$(ARGS)
Any additional command-line arguments.
$(VOICE)
The index of the launched Voice (token only replaced in parallel mode).
$(VOICES)
The Voice count.
$(LOG)
The appropriate syntax for the platform to log the output of that to the left into the log file. For instance, on Windows this token is replaced by "> logfile".
$(ADDR)
The address of the Voice (usually, IP address).
Notes
  • The launch line may be variously modified and augmented as the launcher proceeds (including, but not limited to, replacement of the above tokens). You can retrieve the final form of the launch line from the invocation object returned by the brahms script.
  • Having established the Launch Line that works for your local configuration, you can set LaunchLineSolo, LaunchLineSockets or LaunchLineMPI to have it used as the default for future executions.
  • If you need even more flexibility, you can use the first form of the Launch Line to launch a shell script of your own design, and use this shell script to invoke BRAHMS. This is equivalent to using a Launch Function (below).

Shell Launch Line (Single)

By default, when using Solo, the Launch Line reads

brahms $(MATLAB) $(EXECFILE) $(ARGS)

This will launch BRAHMS to execute the correct Execution File (see notes on tokens, below), and will not return until BRAHMS has finished executing. The launcher will then collect results, collate and return them. This is known as nested launch mode.

If the launch line starts with the five-character token each<space>, the remainder of the line is called once for each voice in the execution, and (naturally) these calls are assumed to return instantly, without waiting for BRAHMS to finish executing. The launcher will then wait until exit files from each voice have been seen, before collecting and returning results. This is known as parallel launch mode. For example, the default Concerto (Sockets) launch line reads

each brahms $(EXECFILE) --voice-$(VOICE) $(ARGS) $(LOG)

Where possible, running in nested mode is preferable, because segmentation faults can be detected (this is not possible in parallel mode). Sometimes, even when running multiple voices (Concerto), it is possible to run in nested mode. An example of this is when multiple voices are launched using MPI. The default Concerto (MPI) launch line reads

mpiexec -n $(VOICES) brahms $(EXECFILE) --voice-mpi $(ARGS)

Shell Launch Line (Multiple)

To use different launch lines for different voices (beyond the variability allowed by replacement of tokens), set exe.launch equal to a cell array of strings. The first will be used to launch Voice 1, the second to launch Voice 2, etc. If insufficient lines are supplied, the last is used to launch all further Voices. Note that this form implies parallel mode, so the launcher will wait for exit files to appear before collecting results. This form might be useful, for instance, if you want to launch the first Voice locally with the GUI displayed, and the remainder on remote machines with the GUI hidden. You could achieve this by setting exe.launch to a two-element cell array.

Launch Function

If you prefer to write a Matlab script rather than a shell command line or script to launch your voices, set exe.launch to a function handle. The function should have the form [err, result] = launch('launch', invocation), will be called just once for all voices, and should launch the number of voices specified in the invocation data object. The function can operate in nested or parallel mode, and should provide a second calling form info = launch('info', invocation), returning a structure info with one string field mode set to either "nested" or "parallel".

In nested mode (e.g. Solo, MPI), the function should launch all BRAHMS voices, wait for them to complete, and return any console output in result. The function can return zero in err on successful completion; if an error occurs in any BRAHMS executable, the error code returned should be returned in err. On failure to launch BRAHMS, the function can simply raise an error.

In parallel mode (e.g. Sockets), the function should launch all BRAHMS voices, not wait for them to complete, and return a cell array in result that holds the final system command executed to launch each voice. err should always be zero on return (error states in the BRAHMS voices will be assessed based on the console output they send to their logs). On failure to launch BRAHMS (any voice), the function can simply raise an error.

Example

M Source Code (against 995)
% construct execution object exe = brahms_execution; % the name is used to generate filenames for XML files exe.name = test; % set the a priori stop time to t = 1.0 seconds exe.stop = 1; % set MultiThread to false exe.execPars.MultiThread = false; % ask for everything to be logged exe.all = true; % set precision of all logs exe.precision = 4; % override settings for one individual log exe = exe.log('process>output', 'precision', 6, 'encapsulated', true); % run a three voice Babble exe.addresses = {'sockets' 3}; % have all processes of Subsystem "SubSys" computed together % have "ProcA" and "ProcB" computed together, too exe.affinity = {{'SubSys'}, {'ProcA' 'ProcB'}}; % as above, but also make sure "SubSys" is computed on Voice 2, % which may be running on particular hardware with which "SubSys" % needs to interact exe.affinity = {{2, 'SubSys'}, {'ProcA' 'ProcB'}}; ... % run BRAHMS out = brahms(sys, exe);

Example

This is an example Launch Line used to invoke BRAHMS on different machines through ssh.

each ssh user@$(ADDR) brahms $(EXECFILE) --voice-$(VOICE) $(ARGS) $(LOG)

Example

This is an example of a Launch Function.

M Source Code (against 995)
% this custom launch script does pretty much exactly what % the default LaunchLineSockets does... function [err, result] = launch(op, invocation) switch op case 'info' info = []; info.mode = 'parallel'; err = info; case 'launch' % our custom launch line (default LaunchLineSockets) % ok, so "start /B" assumes windows... :) cmd = 'start /B brahms $(EXECFILE) --voice-$(VOICE) $(ARGS) $(LOG)'; % modify if isunix q=''''; else q = '"'; end cmd = strrep(cmd, '$(EXECFILE)', [q invocation.exe.executionFile q]); exitfile = [' ' q '--exitfile-' invocation.file.exit q]; % launch all cmds = {}; for v = 1:invocation.exe.voices cmd_ = cmd; cmd_ = strrep(cmd_, '$(ARGS)', [invocation.args exitfile]); cmd_ = strrep(cmd_, '$(LOG)', ['> ' q invocation.file.console q]); cmd_ = strrep(cmd_, '$(VOICE)', num2str(v)); [err, result] = system(cmd_); if err error(result); end cmds{v} = cmd_; end % we have launched in parallel mode err = 0; % no error from executables (yet!) result = cmds; % return launch lines we used end