Given a tuple or list of tuples containing (URL, filename),
    download the given files into the current working directory.
    Downloading is done via astropy's download_file. A symbolic link
    is created in the specified output dirctory that points to the
    downloaded file.

    Parameters
    ----------
    files : tuple or list of tuples
        Each 2-tuple should contain (URL, filename), where
        URL is the URL from which to download the file, and
        filename will be the name of the symlink pointing to
        the downloaded file.

    output_directory : str
        Name of the directory in which to create the symbolic
        links to the downloaded files

    force : bool
        If True, the file will be downloaded regarless of whether
        it is already present or not.

    Returns
    -------
    filenames : list
        List of filenames corresponding to the symbolic links
        of the downloaded files


        A function defined to calculate the scaling factors for SDI cube transformation.
        Parameters
        ----------
        In parameters:
        ----------
        wavelengths : numpy array
        Array with the wavelength of each frame.
        Returns
        -------
        Out
        -------
        numpy array
        Scaling factors.


Function defined to scale the data cube according to
        diffraction limited wavelength scaling relation

        In:
        ----------
        cube_in: 3D numpy array or readcube class

        optional:
        ----------
        shift_back: True/False. If set to True does the inverse shift
        scaling: numpy array of scaling factors as a function of wavelength

        out:
        ------------
        3D numpy array of scaled data cube


circular mask, integer radii only, no fractional flux


	Create a new table fits from a "reference array" (e.g. wavelengths) and a dictionary
	containing arrays of length equal to the reference array (e.g. fluxes of different components).

	:Params:
	  filename: in, type=str
		Name of the output FITS file
	  x: in, type = array
	    reference array (e.g. wavelength array)
	  xname: in, type=1D array
	    name of the reference array x
	  dict_y: in, type=dict
	    dict containing arrays (e.g. flux arrays of different components) of the same length as x.
	    By default, these arrays are assumed to contain floats. To change the format for a given array
	    named "key" in the dict, include another entry named "key_FMT" which specifies its format in dict_y.
	  xfmt: in, optional, type=str
	    format of the reference array x. Default is string.
	  comm: in, optional, type=str
	    A string with any additional information/instructions to be stored in the header.


	Write out a FITS file containing the observed wavelengths and fluxes, the best-fit model, and
	the latter's different components. Names of the components are taken from the config file.

	:Params:
	  wave: in, type=1D array
	    wavelength array
	  flux: in, type=1D array
	    observed flux array
	  best_fit: in, type=1D array
	    best-fit modelled flux array
	  comp_best_fit: in, type=ordered dict
	    ordered dict containing each best-fit component unattenuated, followed by its extinction and absorption
	  config_filename: in, type=str
	    Name of the input config file. This is used to name the output file.


	Write out a txt file containing a table with the best-fit parameters retrieved by lmfit.

	:Params:
	  result: in, type = lmfit model.fit() object
	    model.fit() object obtained from running lmfit. Contains the best-fit parameters result.params
	  config_filename: in, type=str
	    Name of the input config file. This is used to name the output file.


This function takes an xdr template file from .../IDEOS/templates/ and converts it
to a more easily python-readable .npy file. The header is stored as text in a separate .meta file.

In: xdr template file, f.ex. draine03.xdr


    This function takes two test sources 4978688_0.ideos.xdr and IRAS21219m1757_dlw_qst.xdr
    from ../test/test_questfit/ and converts them to a more easily python-readable .npy file.
    Only the 'WAVE', 'FLUX' and 'EFLUX' entries are translated for 4978688_0.ideos.xdr,
    and only the 'WAVE', 'FLUX', 'STDEV' and 'FLAG' entries for IRAS21219m1757_dlw_qst.xdr.


    Author: Nadia L. Zakamska, July 2020
    Inspired by https://github.com/mortcanty/CRCPython/blob/master/src/build/lib/auxil/congrid.py,
    but reworked to work on Python 3x

    Parameters
    ----------
    a : np.array, a multi-dimensional numpy array

    newdims : a tuple with the shape of the new array, must have the same
        dimensionality as the original array a.
        If it doesn't, the code returns the original array.

    method:
        neighbour - closest value from original data
        nearest and linear - uses n x 1-D interpolations using
                             scipy.interpolate.interp1d
        (see Numerical Recipes for validity of use of n 1-D interpolations)
        spline - uses ndimage.map_coordinates

    centre:
        True - interpolation points are at the centres of the bins
        False - points are at the front edge of the bin

    minusone:
        For example- inarray.shape = (i,j) & new dimensions = (x,y)
        False - inarray is resampled by factors of (i/x) * (j/y)
        True - inarray is resampled by(i-1)/(x-1) * (j-1)/(y-1)
        This prevents extrapolation one element beyond bounds of input array.

    Returns
    -------
    np.array with the newdims shape

    Examples:
        1.
        a=np.arange(10)
        newa=rebin(a,(100,))
        2.
        a=np.array([[1.,2.,3.],[2.,3.,4.]])
        newa1=rebin(a,(4,6))
        newa2=rebin(a,(2,3))
        3.
        np.random.seed(seed=200)
        a=np.random.random((2,3,4))
        newa1=rebin(a,(2,3,4))
        newa2=rebin(a,(2,3,8))


Subtracts the PSF from the image at each wavelength slice and returns a PSF subtracted cube


    This function takes a 1D spectrum and stores it under the form of a mock cube
    (with 2 "empty" dimensions). The resulting mock cube can then be fed to readcube.py .

    Parameters
    ----------

    data : recarray
        Input 1D wavelengths, fluxes and errors
        columns named 'WAVE', 'FLUX' and 'EFLUX'
    savename : str
        Name of the output file containing the mock cube


/******************************************************************************
***                     CONSTRUCTOR / DESTRUCTOR                            ***
*******************************************************************************/


//   return RAD2DEG*asin(zarg);
// }


// Parse command line arguments to check if application has been started
// from Metview.


// Remove sync controls which are not part of the session to load.


// Delete actors which are not saved in this session.


// Extract the numbers of the session names.


// remove actor from its current scenes


/* ----- CIE-XYZ <-> Device dependent RGB -----
 *
 *  Gamma Correction
 *
 *  The following two functions provide gamma correction which
 *  can be used to switch between sRGB and linearized sRGB (RGB).
 *
 *  The standard value of gamma for sRGB displays is approximately 2.2,
 *  but more accurately is a combination of a linear transform and
 *  a power transform with exponent 2.4
 *
 *  gtrans maps linearized sRGB to sRGB.
 *  ftrans provides the inverse map.
 *
 */


/* ----- CIE-XYZ <-> sRGB -----
 *
 *  R, G, and B give the levels of red, green and blue as values
 *  in the interval [0,1].  X, Y and Z give the CIE chromaticies.
 *  XN, YN, ZN gives the chromaticity of the white point.
 *
 */


/* ----- CIE-XYZ <-> CIE-LUV ----- */


/* ----- LUV <-> polarLUV ----- */


//NOTE: Parts of this function have been modified in order to use it with
//      Vapor-imported transfer functions!


// Free label resources (GPU and CPU memory).


// This actor is connected to the argument actor if the actor is the
// transfer function of any variable.


// Variable specific properties.


// Check if at least one data source is available with values to load.


// Check for registered data source containing init times, valid
// times and ensemble members.


// Send sync info to each registered synchronized object. Collect those
// objects that will process the sync request (they return true).


/*bool MSceneViewGLWidget::event(QEvent *event)
{
    if (event->type() == QEvent::ToolTip)
    {
        QHelpEvent *helpEvent = static_cast<QHelpEvent*>(event);
        float time = 0.0f;
        std::map<float, QString> depthTextMap;
        foreach (MToolTipPicker *toolTipPicker, toolTipPickers)
        {
            float depth = std::numeric_limits<float>::max();
            QString text;
            if (toolTipPicker->toolTipPick(this, helpEvent->pos(), depth, text))
            {
                depthTextMap.insert(std::make_pair(depth, text));
            }
        }
        depthTextMap.insert(std::make_pair(1e6f, "Test String"));
        QToolTip::hideText();
        if (!depthTextMap.empty())
        {
            QRect rect;
            QToolTip::showText(
                    helpEvent->globalPos(), depthTextMap.begin()->second, nullptr, rect, 10000);
        }
        else
        {
            QToolTip::hideText();
            event->ignore();
        }

        return true;
    }
#ifdef USE_QOPENGLWIDGET
    return QOpenGLWidget::event(event);
#else
    return QGLWidget::event(event);
#endif
}*/


// Loop through all labels and add only those
// which do not overlap with currently selected labels.


/*******************************************************************************
***                         CONSTRUCTOR / DESTRUCTOR
*******************************************************************************/


//Texture::subImage2D(GLint level,
//                    GLint xoffset,
//                    GLint yoffset,
//                    GLsizei width,
//                    GLsizei height,
//                    const GLvoid *data)
//{
//    // bind to last unit?
//    glTexSubImage2D(target, level, xoffset, yoffset, width, height,
//                    format, type, data);
//    // unbind?
//}


/*******************************************************************************
***                        SHADER PROGRAM INFO
*******************************************************************************/


/*******************************************************************************
 ***                      SET UNIFORM SUBROUTINE METHODS
 *******************************************************************************/


// Scan all grib files contained in the directory.


/**
  Fixes a C++ string object that still contains a zero termination character at
  the end. Some attributes read from NetCDF files can show such a behaviour.
  For instance, the time units attribute read with a statement such as 'string
  attribute; var.getAtt("units").getValues(attribute);' could still have a '0'
  value at the last position.

  This method checks if the last character of the given string s is a valid
  ASCII character (value >= 32). If not, the last character is removed.
  */


// To treat rotated grids as regular grids it is necessary for both rotated
// and regular longitude and latitude variables to be recognize as
// longitude and latitude variables respectively. Thus more than one
// standard name is needed at the moment.


// For each file, open the file and extract information about the contained
// variables and forecast valid times.


// Kernel cannot be precomputed as distances between center point and
// surrounding points change depending on geographical position.
// Gauss is implemented as convolution of latitudinal and longitudinal Gauss


// Longitudinal Box Blur smoothing.


//*************************** UNIFORM WEIGHTED SMOOTHING ***********************


// number of ensemble members


/**
 * Finds a root of the cubic polynomial with the passed coefficients.
 * @param x The x coordinate of the Bezier curve.
 * @param b0 Cubic polynomial coefficient 0.
 * @param b1 Cubic polynomial coefficient 1.
 * @param b2 Cubic polynomial coefficient 2.
 * @param b3 Cubic polynomial coefficient 3.
 * @return The t parameter of the Bezier curve at x.
 */


/**
 * Implementation of ray-sphere intersection (idea from A. Glassner et al., "An Introduction to Ray Tracing").
 * For more details see: https://education.siggraph.org/static/HyperGraph/raytrace/rtinter1.htm
 */


/// Removes trailing zeros and unnecessary decimal points.


/// Removes decimal points if more than maxDigits digits are used.


// Release input fields.


// Magnitude of air velocity (3D wind speed; "wind" is defined as 2D only in
// CF).
// =========================================================================


// Equivalent potential temperature
// ================================


// Potential vorticity (LAGRANTO libcalvar implementation)
// =======================================================


// Geopotential height from geopotential
// =====================================


// Dew point temperature
// =====================


// Total precipitation per time interval
// =====================================


// NOTE: surface_air_pressure is requested as a dummy grid to
// initialize the derived grid as a 2D field.


// No synchronization. Reset property colours and disable sync
// checkboxes.


// Request 2: Normals for all scene views that display the trajectories.
// =====================================================================


// This actor is connected to the argument actor if the argument actor is
// the transfer function (scalar to texture) of any variable.


// Extract directory and file filter from given paths.


/* Ownership model specification.
 *
 * Instance objects are ownered by Application's root_ QObject via QObject
 * ownership mechanism. MainWindow is ownered by Instance using
 * std::unique_ptr. When all windows are closed, Application terminates and
 * deletes all its children and all windows are deleted by unique_ptr.
 */


//-----------------------------------------------------------------------------
//constructor por defecto


//constructor con 2 parametros


//constructor con 5 parametros


//hace una busqueda inicial del keyword pyindexf para saber pronto si, en caso
//de error, el programa debe salir o no con exit(1) o exit(0)


//Funcion auxiliar para transformar una longitud de onda de aire a vacio. Las
//unidades de entrada (y salida) son Angstroms.


//-----------------------------------------------------------------------------
//Calcula un percentil pesado del flujo (los pesos sirven para poder manejar
//las fracciones de pixel en los bordes de las bandas: pixels completos tienen
//un peso de 1 y pixels fraccionados tienen como peso la fraccion
//correspondiente). La incertidumbre se calcula mediante simulaciones (solo en
//el caso en el que lerr=true).


//lee las definiciones de los indices del fichero myindexdef.dat o indexdef.dat


//constructor con 4 parametros


//-----------------------------------------------------------------------------
//Calcula un boundary fit, ajustando los datos en el vector vec. El resultado
//del ajuste, evaluado en los mismos pixeles, se almacena en el vector fit.
//Finalmente tambien se evalua el boundary fit en todos los pixeles contenidos
//en el vector eval. De esta forma, este vector puede usarse para calcular un
//unico valor en el centro de una banda, o todo un conjunto de valores.
//Si boundfit > 0, el ajuste es polinomico.
//Si boundfit < 0, el ajuste se realiza con splines.


//-----------------------------------------------------------------------------
//funcion principal: comprueba los parametros de entrada
//Nota: el orden al chequear los parametros debe coincidir con el que aparece
//      en el fichero inputcl.dat.


//lee los valores por defecto de los parametros de entrada del fichero
//inputcl.dat


// Verifica si el usuario ha indicado que la calibracion en longitud de onda
// del espectro ha sido realizada en vacio. Si es asi, se modifican las
// longitudes de onda de todas las bandas a medir.


//-----------------------------------------------------------------------------
//constructor con parametros


//Retorna 0 si estamos ejecutando indexf desde python o value en caso contrario


//! Initialize the response matrices and their generation


//! Analyze the current event


//! Save the responses


//! Return information on the parsable options for this response class


//! Parse the options


//! Finalize the response generation (i.e. save the data a final time )


//! Save the data


//! Check if the first ID has the second one as ancestor


//! Called when an interrupt signal is flagged
//! All catched signals lead to a well defined exit of the program


//! Analyze one events


//! Get the output file prefix


//! Save the response matrices


/******************************************************************************
 * Parse the command line
 */


/******************************************************************************
 * Do whatever analysis is necessary
 */


/******************************************************************************
 * Append a response matrix to this one:
 */


/******************************************************************************
 * Find and join *.rsp files:
 */


/******************************************************************************
 * Find and join *.root files:
 */


/******************************************************************************
 * Divide two response matrices:
 */


/******************************************************************************
 * calculate the Bayesian ratio of two response matrices:
 */


/******************************************************************************
 * Calculate the Probability of two response matrices:
 */


/******************************************************************************
 * Show a response matrix:
 */


/******************************************************************************
 * Collapse a response matrix:
 */


//! Initialize MRotations to rotate source position to (0,0) for all detector coordinates


//! Round double to precision P


//! Shuffle the strips


//! Convert the content to binary


//! Parse the GDMl file


//! Return the data as Geomega file


//! True if we are scaled


//! Return the travel time between the interaction position and the PMTs


//! Read the triggers for a trigger map


//! Set the detector list


//! Set a trigger, veto, etc.


//! Return true if this trigger is triggering (not vetoing)


//! Return true if this trigger is vetoing


//! Returns true if the hit could be added


//! Set a component by atomic weighting


//! Set a component by atomic weighting with natural composition


//! Set a component by mass weighting


//! Set a component by mass weighting with natural composition


//! Set most of the variables:


//! Set that this detector has a guard ring


//! Check if all input is reasonable


//! Set a flag indicating that vetoes are ignored and transfer it to all triggers


//! Return true if this detector is never triggering


//! Return a list of all the triggers which have been raised


//! Return a list of all the vetoes which have been raised


//! Set the weighting by mass


//! Set the weighting by atoms


//! Write some text and clear the stream


//! Write some text


//! Check if the time is withing a good interval


//! Add this GTI file's intervals


//! Load the good time interval data


//! Division operator, return a new quaternion by dividing this quaternion by Q


//! Return the inverse of this quaternion


//! Return the unit quaternion of this quaternion


//! Return a rotation matrix


//! Spherical linear interpolation between two quaternions, T is the distance between Q1 and Q2 in [0, 1]


//! Check for equality


//! Less than operator for sorting!


//! Return the element name


//! Add line parameters:


//! Return the line energy


//! Return the line exclude flag


//! Return the default line, or -1 if non could be found


//! Return the line branching ratio


//! Dump the content into a string


//! Return the string between two strings


//! Replace the string "From" at the end of the string with "To", if "From" is at the end of the string


//! Check if we have equal bins


//! Create the binning


//! Find a bin


//! Return axis bins edges for external drawing


//! Return the bin center(s) of the given axis bin
//! Can throw: MExceptionIndexOutOfBounds


//! Returns all bin centers as vector


//! Show a histogram of the data


//! Clone this axis


//! Set the axis in FISBEL mode


//! Return the axis bins for drawing --- those might be narrower than the real bins


//! Test if theta and phi (in degree) are within the range of the axis - the second value is required


//! Write the content to a stream


//! Convert to a human readable string


//! Get a specific event


//! Get an 8-bit int


//! Get an 8-bit unsigned int


//! Add an 16-bit int


//! Get an 16-bit int


//! Add an 16-bit unsigned int


//! Add an 32-bit int


//! Get an 32-bit int


//! Add an 32-bit unsigned int


//! Get an 32-bit unsigned int


//! Add an 64-bit int


//! Get an 64-bit int


//! Add an 64-bit unsigned int


//! Get an 64-bit unsigned int


//! Add a float


//! Get a float


//! Add a double


//! Get a double


//! Add a MVector as 3 floats


//! Get a MVector from 3 floats


//! Add a MVector as 3 doubles


//! Get a MVector from 3 doubles


//! Add a string


//! Get a string


//! Add a character


//! Add an array of characters


//! Get a character


//! Move the reading position pointer


//! The actual histogramming process - default just makes one bin


/******************************************************************************
 * Return true if the matrix really is (within tolerances) a rotation matrix
 * i.e. det A = +1, A*A_inv = I
 */


/******************************************************************************
 * Return an inverted matrix without touching this one
 */


/******************************************************************************
 * Perform an additional rotation by an angle (in rad) along a vector
 */


/******************************************************************************
 * Check for equality
 */


//! Clear all data sets


//! Set the minimum and maximum. If Adapt is true, then use for
//! min=max(m_Minimum, real minimum)
//! max=min(m_Maximum, real maximum)
//! Adapt will not take place if there is no data between minimum and maximum
//! If Maximum <= Minimum no changes will take place to the data


//! Add unsorted x value data


//! Return as a histogram (cts)


//! Return as a normalized histogram (e.g. cts/bin width)


//! Draw normalized histogram (e.g. cts/bin width)


//! Return the binned data as a vector


//! Return the bin edges as a vector


//! Rotate vector with axis Axis by angle Angle


//! Check if the vectors are orthogonal with a tolerance


//! Set the bin edges


//! Set the axis in linear mode


//! Set the axis in logarithmic mode


//! Return the axis bin given a axis value


//! Return the area of the given axis bin


//! Test if the x-value is within the range of the axis


//! Return the minimum axis values


//! Switch to sparse mode


//! Switch to non-sparse mode


//! Find the axes bins corresponding to the sparse Bin


//! Set the content of a specific bin -- directly without error checks
//! Logic: a1 + S1*a2 + S1*S2*a3 + S1*S2*S3*a4 + ....


//! Add to the content of a specific bin -- directly without error checks
//! Logic: a1 + S1*a2 + S1*S2*a3 + S1*S2*S3*a4 + ....


//! Add a collection of bin values


//! Set the content of a sparse bin


//! Add to the content of a sparse bin


//! Get the content of a specific bin -- directly without error checks
//! Logic: a1 + S1*a2 + S1*S2*a3 + S1*S2*S3*a4 + ....


//! Sort the sparse matrix


//! Given an order, return the axis it belongs to


//! Return a string with statistics numbers


//! Load all isotopes form a standard MEGAlib isotope file


//! Return true if the store contains the isotope


//! Determine the maximum and its coordiantes, the vector is filled up to the number of dimensions the histogram has


//! Write some basic data to the file/stream


/******************************************************************************
 * Print a pretty "Assertion failed" message
 * e.g. Assertion failed in file ZDObst.cpp at line 135:
 *          Condition "Apfel == Birne" not fulfilled!   Aborting!
 */


//! Return true if the file was removed successfully


//! Return true is the file is good


//! Seek the given position


//! Flush all written text


//! Get one character


//! Get one float


//! Get transmission probability a value


//! Set all data


//! Reset to default values


//! Parse a line
//! Returns 0, if the line got correctly parsed
//! Returns 1, if the line got not correctly parsed


//! Stream to a file
//! Reading has to be done in the derived class


//! Perform a Thomson Tau test
//! Requires at least two input value
//! Return for each value if it is an outlier


//! Dump the content into a string


//! Set the input of one specific input node for all networks


//! Run, i.e. create the output


//! Return the output of one specific node (numbering starts with zero)


//! Set the output of one specific input node for learning for all networks


//! Set the output error of one specific node for all networks


//! Do the learning --- we will not decide if the learning was sufficient!


//! Save the store


//! Load the store


//! Return a neural network IO --- throw an exception otherwise


//! Get an instance of this singleton


//! Get the default font


//! Get the emphasized font


//! Get the italic medium font


//! Get the italic bold font


//! The default constructor


//! Set the number of progress bars


//! Set the Name of the given progress bar ID
//! If it doesn't exist, throw an exception MExceptionIndexOutOfBounds


//! Set the minimum and maximum value for the given progress bar ID
//! If it doesn't exist, throw an exception MExceptionIndexOutOfBounds


//! Set the current value for the given progress bar ID
//! If it doesn't exist, throw an exception MExceptionIndexOutOfBounds


//! Process all messages for this UI


//! Bring the GUI to the screen


/******************************************************************************
 * Called when an interrupt signal is flagged
 * All catched signals lead to a well defined exit of the program
 */


/******************************************************************************
 * Return the number of non comment tokens
 */


/******************************************************************************
 * Analyze the event, return true if it has to be writen to file
 */


//! Set the name of background type


//! Set background file observation time


//! If the event passes the event selction criteria,


//! If the event passes the event selection criteria,


/******************************************************************************
 * Generate a list of master files, which contain only events which
 * fullfill the requirements in the configuration file:
 */


/******************************************************************************
 * Generate one master file
 */


/******************************************************************************
 * Do all the discretization:
 */


/******************************************************************************
 * Does the same as UHTOC in Geant3
 */


/******************************************************************************
 * Do the tracked events analysis
 */


//! Parse the command line


//! Do whatever analysis is necessary


//! initialize command line arguments


/******************************************************************************
 * Layout all daughter volumes
 */


/******************************************************************************
 * Generate a on of map
 */


/******************************************************************************
 * Split a volume
 */


/******************************************************************************
 * Calculate the anti correlation function
 */


//! Clear the content


//! Clone this calibration - the returned calibration must be deleted!


//! Add a spectral point to the read-out data group


//! Get the number of spectral points in the roud-out data group


//! Remove a point - the check if they are indentical is soly based on the peak position.


//! Return the calibration in a saveable format
//! Mode: pak  - points ADC to keV
//! Mode: pakw - points ADC to keV and fwhm
//! Mode: model - show the model (none, poly2, poly3, poly2gauss, etc.)


//! Get a list of all unique spectral points in this spectrum


//! Set the energy calibration model


//! Remove the energy calibration model


//! Set the FWHM calibration model


//! Remove the FWHM model


//! Set the background model
//! If it doesn't exist don't use any


//! Set the energy loss model
//! If it doesn't exist don't use any


//! Return the number of fit parameters in the background fit


//! Return the number of fit parameters in the energy loss fit


//! The function for fitting the background


//! The function for fitting the energy loss


//! Set all fit parameters


//! Get a value at the given x


//! Mimic ROOT Draw functionality


//! Clone this read-out element - the returned element must be deleted!


//! Smaller than operator


//! Return true if this read-out element is of the given type


//! Parse the data from the tokenizer


//! Return the data as parsable string


//! Convert to a string


//! Clear the content of this read-out element


//! Clone this element


//! Dump the content into a parsable string


//! Fit the given histogram in the given range - return the quality of the fit


//! Get the fit value - return 0 if the fit does not exist


//! Return a parsable string


//! Remove all data


//! Add a new read-out element and a dummy calibration, if the read-out element exist, do nothing


//! Remove the calibration of the read-out element and replace it by a dummy one


//! Add a new read-out element and calibration, if the read-out element exits, then replace the calibration


//! Returns the index of a calibration by its associated read-out element
//! If the read-out element does not exist, return g_UnsignedIntNotDefined


//! Create a histogram from the read-out data group using a fixed number of counts per bin


//! Add a read-out data group and the associated isotopes


//! Remove all content


//! Find a read out with the given read-out element and return its position
//! Return g_UnsignedIntNotDefined in case it is not found


//! Remove a read out


//! Return true if all read-out elements are of the same type


//! Parse a line - return true if the line was processed (irrelevant if successful)


//! Open the file


//! Perform the calibration


//! Test for equality


//! Remove all collected data


//! Add a group to all collections and return its ID


//! Move the content of the read-out data store to this ones GroupID
//! Group ID must exist, and the store must only have one own group at position 0


//! Add the data of a read-out sequence to the store


//! Check if the given read-out element is in the collection


//! The copy constructor


//! Move the content from the given into this read-out data group


//! Add another read-out element type


//! Add another read-out data type


//! Return true if this kind of read-out element is registered


//! Return true if this kind of read-out data is registered


//! Return the new instance of this read-out element
//! Return zero if it doesn't exist, it must be deleted


//! Return the new instance of this read-out data
//! Return zero if it doesn't exist, it must be deleted


//! Find the peaks in this read-out data group


//! Fit the peaks in this read-out data group


//! Do a final check of all peaks


//! The function for ROOT fitting


//! Number of parameters of the fit


//! Fit the given histogram in the given range


//! Get the FWHM


//! Convert content to a string


// Return false if the newly added point would result in a negative incline


//! Constructor setting the read out element and data


//! Set the read-out element


//! Set the read-out data


//! Add a read-out group and return its ID


//! Add this read-out data


//! Add all possible roud-out datas (i.e. those with identical sequence) of this read-out sequence


//! If the read out has the correct ROE add it


//! Move all read outs of this read-out data group
//! If g does not exist return an MExceptionIndexOutOfBounds exception


//! Return the combined type of this read-out data and its wrapped data


//! Return this read-out data as the given type - return nullptr if not possible


//! Thread entry point for the parallel calibration


//! Clear the data


//! Load the calibration data containing the given isotopes - return false if an error occurred
//! This function performs parallel loading of all given files


//! Perform the calibration of the given collection


//! Draw the spectrum of all read-out data groups in the collection into the given canvas


//! Return true if we have an energy calibration model


//! Return true if we have an FWHM calibration model


//! Get the number of calibration point in the spectra


//! Draw the line fit into the Canvas for the given Collection


//! Return the calibration fit quality


//! Draw the calibration into the Canvas for the given Collection


//! Perform parallel spectrum creation


//! Create the histogram for the given read-out data group


//! Given an existing calibration for the collection, do a reassignment of energies and determination of the model


//! Save the calibration in e-cal format


//! Set a Quality factor representing the color of the elemnt


//! Handle button presses in the canvas


//! Add the isotopes to the combo box


//! Action after the Apply or OK button has been pressed.


//! Create the selection GUI element


//! Handle all key presses


//! Update the setting with the GUI data


//! Close the applictaion


//! Switch the histogram binning mode


//! Toggle the log display of the histogram x-axis


//! Toggle the log display of the histogram y-axis


//! Choose the calibration files and isotopes


//! Actions when the save button has been pressed


//! Action when one of the ROE buttons was pressed


//! Action when the next button has been pressed


//! Action when the back button has been pressed


//! Actions when the next fit button has been pressed


//! Actions when the previous fit button has been pressed


//! Actions when the toggle-line button has been pressed


//! Update the histogram with the latest settings


//! Update the peakhistogram with the latest settings


//! Update all graphs


//! Set the active collection and put it to the screen


//! Update the line fit


//! Update the calibration


//! Switch to the line near the given X value


//! Fit the current histogram


//! Load a configuration file from disk


//! Create or re-create the view


//! Set the quality of an element


//! Process the messages for this UI, mainly the scollbar moves:


//! Set all calibration files, group IDs, and Isotopes at once


//! Read the configuration data from an XML node


//! Create an XML node tree from the configuration


//! Global function to start the thread


//! Return true if this module is a hard predecessor


//! Return true if this module is a soft predecessor


//! Set the energy histogram parameters


//! Set the processing time


//! Set the number of instances


//! Run a single tests


//! Run all tests


//! Test a single fit


//! Set the number of subsets:


//! Randomly shuffle the events


//! Do not apply any Earth horizon tests


//! Reject all events whose cone is below or intersects the horizon


//! Reject all events who have a certain probability to come from Earth.


//! Set the position of Earth in detector coordinates and
//! the azimuthal angle of the horizon realtive to this position


//! Return true if the event originates from Earth


//! Return true if the event originates from Earth via intersection test


//! Return true if the event originates from Earth via probability test


//! Create the imager


//! Save the peak heights


//! Set the test position, and its coordinate system


//! Fit this function to the data
//! The ID corresponds to the position of the corresponding MARMFitFunctionID in the vector retuned by GetListOfFitFunctions()
//! If it's not in there use c_AsymmetricGaussLorentzLorentz


//! Reset the internally stored ARM values


//! Optimize binning - check sif the binning is OK, otherwise check for a better one


//! Return the name of the fit given the fit function ID


//! Return the function of the fit given the fit function ID


//! Return the number of parameters of the fit given the fit function ID


//! Get a list of all fit functions:


//! Switch between the fit functions


//! Setup a Gauss fit function


//! Setup a Lorentz fit function
//! Return: The fitter


//! Setup a generalzied normal distribution fit function


//! Setup an Gauss-Lorentz fit function


//! Setup an Gauss-Double-Lorentz fit function


//! Setup an Asymmetric-Gauss-Double-Lorentz fit function


//! Setup an Asymmetric-GeneralizedNormal+GeneralizedNormal fit function


//! Perform a series of fits to find the best match


//! Perform fits with all fit functions and report Baker-Cousin likelihood ratios


//! Bootstrap the ARM values and return them as vector


//! Calculate all ARM metrics from the bootstrapped results


//! Calculate all ARM metrics from the distribution itself


//! Performs N fits. N must be 1 or larger.
//! Each fit samples randomly from the stored ARM values to determine the average width and error correctly


//! Convert the results into a string


//! Draw the ARM histogram


//! Load the ARM value from file


//! Save the the ARM values to a file


//! Set the viewport / image dimensions


//! Return a copy of the current exposure map


//! Set the efficiency file and switch to that mode


//! Create the exposure for one event


//! Apply the exposure


//! A distance metric to determine when we have to recalculate
//! The value is just the largest difference between the axis vectors


//! Get the efficiency - theta and phi are in detector coordinates


//! The resolution measure for PET events


// Create an orientation file for cosima from an existing observation


//! Calculate the origin probabilities for a PET event


//! Calculate the origin probabilities for a multi-event event


//! Special version of exp for Gauss-calculations: exp(-x) --> this input x has to be positive!!
//! We have a cut-off at x = 10.4: y < 0.00003 -> y = 0
//! The cut-off is at the absolute accuracy limit of the algorithm


//! Set the number of threads


//! Return the string as method, if not found c_Unknown is returned


//! Return the method as a string, if not found "Unknown" is returned


//! Set all used modes


//! Return all methods as a vector


//! Set all used methods


//! Return true if the method is used


//! Return the used methods as a string


//! Return the used methods as a vector


//! Return the number of used TMVCA methods


//! Return true if any of the raw event incarnations is valid


//! Set the distance cut off


//! Do the analysis - this will add events to the whole incarnation list


// Create for the given sequence length, 2..N


// Fill the data sets from RESEs


//! Fill the evaluation section, whether the event is competely absorbed


// Create the tree


//! Get the volume sequence:
//! If it we have a start point, its the VS of the start point, other wise the VS of the first end point, otherwise the VS of the first RESE


//! Append a track to the endpoint AND adds the hit to this Track AND removes them from the track!


//! Return true if any of the raw events is valid


//! Set the file name for TMVA analysis


//! Write the currently loaded data set to a string


//! Set origin information


//! Return the REAM at position a


//! Delete a REAM


//! Remove and return a REAM


/******************************************************************************
 * Open all files and reset the instance
 */


/******************************************************************************
 * Write the file header of the sim file
 */


/******************************************************************************
 * Set the collection ID of the hits
 */


/******************************************************************************
 * Set the function to which we relegate the events
 */


/******************************************************************************
 * Things to do before the start of a new event (reset last event data)
 */


/******************************************************************************
 * Reset all per event data
 */


/******************************************************************************
 * Add an IA information to the current event
 */


/******************************************************************************
 * Set the Galactic pointing --- this is in degree as is does not translate well into radians (e.g. -90 lat)
 */


/******************************************************************************
 * Set the Detector orientation --- this is in degree for congruence reasons with SetGalacticPointing
 */


/******************************************************************************
 * Add a deposit in passive material to the event data
 */


/******************************************************************************
 * Add an energy loss
 */


/******************************************************************************
 * Abort the current event
 */


/******************************************************************************
 * Test for trigger and store all events
 */


/******************************************************************************
 * Save the event to file (only saves the event if we really want to)
 */


/******************************************************************************
 * Transmit event via TCP/IP (only transmit it if we have an open transceiver)
 */


/******************************************************************************
 * Initialize all members to default values
 */


/******************************************************************************
 * Add a track ID as origin to this hit
 */


/******************************************************************************
 * Add several origins to the list
 */


/******************************************************************************
 * Return a hit
 * Call this function in the derived class and fill the remaining data
 */


/******************************************************************************
 * Initialize the program
 */


/******************************************************************************
 * Set an event relegator function (i.e. your own event handler)
 */


/******************************************************************************
 * Execute the macro or parameter file
 */


/******************************************************************************
 * Interrupt the run at the end of the next event
 */


/******************************************************************************
 * Only initializes all members to default (non-set) values
 */


/******************************************************************************
 * Assign all values of the left hand side hit to this one
 */


/******************************************************************************
 * Compare two hits, whether they are within the same voxels of the layer, i.e.
 * only voxels and detector name are compared
 */


/******************************************************************************
 * Return a guard ring hit
 */


/******************************************************************************
 * Return a hit
 */


/******************************************************************************
 * The printed information string look like:
 * Hit in Layer bachus near voxels 12/45, real: (3.6/6.4/12.4) with 231.4 keV
 */


/******************************************************************************
 * Register the graphics to the system
 */


/******************************************************************************
 * Set name, type and collection
 */


/******************************************************************************
 * Create hit collection if not yet done
 */


/******************************************************************************
 * Process the hit: Don't do anything
 * This quirk is necessay since in the Geant4 SteppingManager the hits are
 * processed before the UserSteppingAction is called, and for storing the
 * correct IA information, we must first update the track information
 */


/******************************************************************************
 * Process the hit: Center positions, generate a hit and
 * add it to the hit collection
 */


/******************************************************************************
 * Transfer hits to Geant
 */


/******************************************************************************
 * Perfrom the conversion from Geant4 to MEGAlib
 */


/******************************************************************************
 * Convert the shape
 */


/******************************************************************************
 * Convert an orientation
 */


/******************************************************************************
 * Convert very small numberes to zero
 */


/******************************************************************************
 * Create an unique material name:
 */


/******************************************************************************
 * Create an unique logiocal volume name:
 */


/******************************************************************************
 * Create an unique physical volume name:
 */


/******************************************************************************
 * Convert the name to MEGAlib conventions
 */


/******************************************************************************
 * Compare two hits, whether they are within the same bar of the module, i.e.
 * only bars and detector names are compared
 */


/******************************************************************************
 * The printed information string look like:
 * ...
 */


/******************************************************************************
 * Basically only initialize the hit collection
 */


/******************************************************************************
 * Process the hit: Center, check if the hit did not happenend in the
 * guard ring, generate a hit and add it to the hit collection
 */


/******************************************************************************
 * Standard housekeeping of event action for geant
 */


/******************************************************************************
 * Only calls the base class constructor
 */


/******************************************************************************
 * If during the step a Compton or pair process happend in the primary track,
 * the process information (positions, direction, energies) are transmitted
 * to the event action class, for later file output
 */


/******************************************************************************
 * Return the Cosima particle type ID from the particle name
 */


/******************************************************************************
 * Return the cosima particle type ID from the particle definition
 */


/******************************************************************************
 * Returns the Geant4 particle definition from a MEGAlib particle ID
 */


/******************************************************************************
 * Return the Id of the detector, we are currently in
 */


/******************************************************************************
 * Default constructor: Does nothing
 */


/******************************************************************************
 * Register the selected processes
 */


/******************************************************************************
 * Construct the processes - overwritten to post-modify some processes
 */


/******************************************************************************
 * Only the default cuts are implemented right now
 */


/******************************************************************************
 * Default Geant4 Construct Method, returns the world volume
 */


/******************************************************************************
 * Should be directly called after constructor:
 * Initializes the geometry
 */


/******************************************************************************
 * Create a rotation matrix
 */


/******************************************************************************
 * Recursively position all volumes - in the it smother volumes
 */


/******************************************************************************
 * Return a random position in the given volume
 */


/******************************************************************************
 * Return true if the volume is valid volume in the geometry
 */


/******************************************************************************
 * Return the (Geomega) hash of the given material
 */


/******************************************************************************
 * Default constructor, which only sets the name and the type to Unknown
 */


/******************************************************************************
 * Create all particles which can appear during the simulation
 */


/******************************************************************************
 * Define all transportation processes for all particle types based on
 * electronmagnetic interaction
 */


/******************************************************************************
 * Not yet implemented
 */


/******************************************************************************
 * The equal operator checks only the base data, not the production rate,
 * count, activation or storage markers!!
 */


/******************************************************************************
 * Return the decay constant
 */


/******************************************************************************
 * Return if the particle is stable
 */


/******************************************************************************
 * Do some initializations for the next run
 */


/******************************************************************************
 * Activate the beam and work on all activators and runs included in the file
 */


/******************************************************************************
 * Default constructor - does nothing
 */


/******************************************************************************
 * Return true, if the duration could be set correctly
 */


/******************************************************************************
 * Return true, if the triggers could be set correctly
 */


/******************************************************************************
 * Return true, if the events could be set correctly
 */


/******************************************************************************
 * Set the activation mode
 */


/******************************************************************************
 * Add a source to the list - by name and only if it does not exist already
 */


/******************************************************************************
 * Get a specific source
 */


/******************************************************************************
 * Return true, if the geometry file could be set correctly
 */


/******************************************************************************
 *  Add an event to an event list (used for activation simualtion)
 */


/******************************************************************************
 *  Add an event to an event list (used for activation simualtion)
 *  Return true if new source has been added
 */


/******************************************************************************
 * Add an element to the radioactive particle store
 */


/******************************************************************************
 * Check if a file with the given name already exists, and give the new
 * incarnation of the file:
 */


/******************************************************************************
 * Save the isotope store, if it has a name
 */


/******************************************************************************
 * Check stop conditions
 */


/******************************************************************************
 * Dump a Run statistics
 */


/******************************************************************************
 * Generate the start vertex(ices) (energy, position, momentum, polarisation)
 * for a new event by using the particle gun
 */


/******************************************************************************
 * Set whether this is a 3D detector or not
 */


/******************************************************************************
 * Compare to hits, whether they are within the detector, i.e.
 * only the detector names are compared
 */


/******************************************************************************
 * The printed info string looks like:
 * Hit in Scintillator "zefal" with 6546.3 keV
 */


/******************************************************************************
 * Return the particle definition generated from the Cosima ion ID, zero otherwise
 */


/******************************************************************************
 *  Clear the store
 */


/******************************************************************************
 * Return the particle definition generated for the given volume, ID, and excitation
 */


/******************************************************************************
 *  Add a new particle to the store
 */


/******************************************************************************
 *  Save the store to disk
 */


/******************************************************************************
 *  Load the store from disk
 */


/******************************************************************************
 * Scale (multiply) to content by a certain factor S
 */


/******************************************************************************
 * Add an IsotopeStore
 */


/******************************************************************************
 *  Create a source list assuming the value is an activity in Bq
 */


/******************************************************************************
 *  Create a source list assuming the value is an isotope
 */


/******************************************************************************
 * Return the number of IDs for a given volume:
 */


/******************************************************************************
 * Return a volume name:
 */


/******************************************************************************
 * Return an ID for a given volume:
 */


/******************************************************************************
 * Return an excitation for a given volume, and ID:
 */


/******************************************************************************
 * Return the value for a given volume:
 */


/******************************************************************************
 * Remove all stable elements:
 */


/******************************************************************************
 * Compare two hits, whether they are within the same strips of the layer, i.e.
 * only strips and detector name are compared
 */


/******************************************************************************
 * The printed information string look like:
 * Hit in Layer bachus near strips 12/45, real: (3.6/6.4/12.4) with 231.4 keV
 */


//! Set everything to default


//! Read a list of orientations from file


//! Check if Time is covered in the time array


//! Find the closest index, always check with InRange(Time) first to avoid exceptions!


//! Get the orientation


//! Perform the orientation for the given time from local to oriented coordinate system


//! Perfrom the inverted orientation for the given time from oriented to local coordiante system


//! Perfrom the orientation for the given time


//! Perfrom the inverted orientation for the given time


//! Return the start time or zero if there is none


/******************************************************************************
 * Set the activation mode ConstantIrradiation
 */


/******************************************************************************
 * Set the activation mode ConstantIrradiationWithCoolDown
 */


/******************************************************************************
 * Set the activation mode TimeProfile
 */


/******************************************************************************
 * Set one of the files containing the counts
 * You can add as many files as you wish
 */


/******************************************************************************
 * Load the counts file
 */


/******************************************************************************
 * Calculate the activation rates after X time activation
 */


/******************************************************************************
 * Dump the tree
 */


/******************************************************************************
 * Clean the trees calculated during decay chain determination
 * Return true if the tree has changed
 */


/******************************************************************************
 * Calculate the activation using random numbers
 */


/******************************************************************************
 * Determine the half life of the particle
 */


/******************************************************************************
 * Calculate the activation using equations (works up to 5 elements)
 */


//bool MCActivator::ActivateByNumericalIntegration(vector<MCActivatorParticle>& P, double ActivationTime, double CooldownTime)


/******************************************************************************
 * Determine the counts of the first produced element after Time t
 */


/******************************************************************************
 * Determine the activation of the first produced element after Time t
 */


/******************************************************************************
 * Determine the activation of the second produced element after Time t
 */


/******************************************************************************
 * Construction by name
 */


/******************************************************************************
 * In the case this is the delayed events list, check if the source
 * is compatible with the NEXT particle and if yes set an event to be skipped
 */


/******************************************************************************
 * Generate the particle of this source for the particle gun
 */


/******************************************************************************
 * Set the type of the start area from ehich the photons start in the far field
 */


/******************************************************************************
 * Return true, if the start area vector could be set correctly. For a
 * description of the meaning of the parameters see the documentation.
 */


/******************************************************************************
 * Upgrade the start area parameters and do some sanity checks
 */


/******************************************************************************
 *  Return true, if the particle type could be set correctly
 */


/******************************************************************************
 * Return the name of the spectrum (e.g. mono, etc.)
 */


/******************************************************************************
 * Return true, if the coordinate system could be set correctly
 */


/******************************************************************************
 * Return true, if the particle type could be set correctly
 */


/******************************************************************************
 * Return true, if the region type could be set correctly
 */


/******************************************************************************
 * Return the name of the beam (e.g. point, line, etc.)
 */


/******************************************************************************
 * Return the name of the beam in similar format as given in the source file
 */


/******************************************************************************
 * Return true, if the position vector could be set correctly. For a
 * description of the meaning of the parameters see the documentation.
 */


/******************************************************************************
 * Return true if the combined normalized energy-beam-flux-function could be set
 */


/******************************************************************************
 * Return true, if all tests and upgrades for the position parameters
 * are sucessfull
 */


/******************************************************************************
 * Return true, if the file containing the spectrum could be set correctly
 */


/******************************************************************************
 * Return the specific position parameter
 */


/******************************************************************************
 * Return true, if the energy vector could be set correctly. For a
 * description of the meaning of the parameters see the documentation.
 */


/******************************************************************************
 * Return true, if all tests and upgrade to the energy parameters could be
 * performed
 */


/******************************************************************************
 * Return the specific energy parameter
 */


/******************************************************************************
 * Return true, if the flux could be set correctly
 */


/******************************************************************************
 * Return true, if the enhanced flux calculations could be performed
 */


/******************************************************************************
 * Return true, if the intensity could be set correctly
 */


/******************************************************************************
 * Return true, if the far field transmission probability file could be set and read correctly
 */


/******************************************************************************
 * Return true, if the light curve could be set correctly
 */


/******************************************************************************
 * Return true, if the enhanced light curve calculations could be performed
 */


/******************************************************************************
 * Set the polarization, the first parameter indicates, if the vector is
 * in absolute coordinates (true) or relative to the flight direction (false)
 *  Return true, if the particle type could be set correctly
 */


/******************************************************************************
 * Return the name of the polarization (e.g. mono, etc.)
 */


/******************************************************************************
 * Return true, if the position vector could be set correctly
 */


/******************************************************************************
 * Set the degree of polarization 1.0 == 100% polarized
 */


/******************************************************************************
 * Set entries of the event list from file
 */


/******************************************************************************
 * Set an entry of the event list
 */


/******************************************************************************
 * Set the isotope count - promotes this source to an isotope count
 */


/******************************************************************************
 * Return the time to the next photon emission of this source:
 * The error in this routine is <= Scale
 */


/******************************************************************************
 * Generate a particle in the particle gun
 */


/******************************************************************************
 * Generate the particle definition
 */


/******************************************************************************
 * Return the mean produced energy:
 */


/******************************************************************************
 * Generate an inititial energy in the particle gun
 */


/******************************************************************************
 * Generate an inititial position in the particle gun
 */


/******************************************************************************
 * Generate an inititial polarization in the particle gun
 */


/******************************************************************************
 * Perform an orientation of the vector from local into oriented coordinate system
*/


/******************************************************************************
 * Perform an orientation of the vector from local into oriented coordinate system
 */


/******************************************************************************
 * Shape of black body emission (Temperature in keV)
 */


/******************************************************************************
 * Shape of a Band function
 */


/******************************************************************************
 * Shape of a Comptonized spectrum
 */


/******************************************************************************
 * Default constructor - the parsing of the file takes place in Parse()
 */


/******************************************************************************
 * Parse the Run file and return true, if everything went right
 */


/******************************************************************************
 * Return a run per name or zero if it does not exist
 */


/******************************************************************************
 * Remove all but the given run from the list
 */


/******************************************************************************
 * Return an activator per name or zero if it does not exist
 */


/******************************************************************************
 * Return a region per name or zero if it does not exist
 */


/******************************************************************************
 * Return a source per name or zero if it does not exist
 */


/******************************************************************************
 * Actions before tracking starts
 */


/******************************************************************************
 * Run all tests
 */


/******************************************************************************
 * Create a source file
 */


/******************************************************************************
 * Create a spectrum
 */


/******************************************************************************
 * Power law test
 */


//! Set line found


//! Return if the line has been found


/******************************************************************************
 * Convert the phantom into MEGAlib/Geomega format
 */


/******************************************************************************
 * This function is just an example on how to use the relegation of a just simulated event
 */


/******************************************************************************
 * Build the background model from the current data set
 */


/******************************************************************************
 * Prepare the response:
 * (1) Read
 * (2) Normalize to the ratio of counts detected vs emitted per bin
 */


/******************************************************************************
 * Create the response matrix for a single event
 */


/******************************************************************************
 * Prepare the response:
 * (1) Read the events and prepare the response slices
 */


/******************************************************************************
 * Parallel response rotation
 */


/******************************************************************************
 * Create the Galactic response
 */


/******************************************************************************
 * Parallel background model rotation
 */


/******************************************************************************
 * Create an exposure map
 */


/******************************************************************************
 * Reconstruct the image in RL mode
 */


/******************************************************************************
 * Reconstruct the image in MEM mode
 */


/******************************************************************************
 * Reconstruct the image in LR mode
 */


/******************************************************************************
 * Reconstruct the image
 */


/******************************************************************************
 * Show an image in Galactic coordinates
 */


//! Show what we have


//! Save the data cell


//! Create the data cubes


/******************************************************************************
 * Generate an albedo photon spectrum after Ajello et al. 2008 & Mizuno 2004
 * Mizuno is used as the absolute normalization and the Ajello shape is scaled
 * to the Mizuno normalization
 */


/******************************************************************************
 * Generate an albedo photon spectrum after Tuerler+ (A&A 512, A49, 2010) & Mizuno 2004 & Abdo (PHYSICAL REVIEW D80, 122004, 2009)
 * Mizuno is used as the absolute normalization and the Ajello shape is scaled
 * to the Mizuno normalization
 */


/******************************************************************************
 * Generate a cosmic photon spectrum after Gruber et al. 1999
 */


/******************************************************************************
 * Generate an albedo electron spectrum after Alcaraz et al. 2000 & Mizuno 2004
 */


/******************************************************************************
 * Generate an albedo positron spectrum after Alcaraz et al. 2000 & Mizuno 2004
 */


/******************************************************************************
 * Generate an albedo proton spectrum after Alcaraz et al. 2000
 */


/******************************************************************************
 * Generate an albedo proton spectrum after Alcaraz et al. 2000
 * Combines and averages up and downward component
 */


/******************************************************************************
 * Generate an albedo proton spectrum after Mizuno+ 2004
 * Combines and averages up and downward component
 */


/******************************************************************************
 * Generate an albedo neutron spectrum after Morris and Kole
 */


/******************************************************************************
 * Generate an albedo neutron spectrum after Kole
 */


/******************************************************************************
 * Generate a cosmic electron file from Mizuno 2004
 */


/******************************************************************************
 * Generate a cosmic positron file from Mizuno 2004
 */


/******************************************************************************
 * Generate a cosmic proton spectrum from SPENVIS files
 */


/******************************************************************************
 * Generate a cosmic alpha particle spectrum from SPENVIS files
 */


/******************************************************************************
 * Generate an average trapped protons and electrons spectrum from SPENVIS files
 */


/******************************************************************************
 * Check if the chosen spectrum is within the validity range model
 */


/******************************************************************************
 * Write the final summary files
 */


//Merge two old components into a new component.


//  Save volume information to text file.


//  Sorting nodes based on a member value of the class Node.


//Save to file points that belong to components that touch box boxes.


//  Gather information about volume of connected components touching both regions into vector of volumes.


// Checking if a node is in region A or in region B.


//  Checking if both connected components touch region A and region B.


//  Finding root (parent) of connected component using a recurisve functon.


//? Set x = y


//? y = ax


//! Read Leja points from file


//? Power Iterations


//? Real Leja Phi NL (Nonhomogenous linear equations)


//? Real Leja Exp (Homogenous linear equations - matrix exponential)


//? Solvers without an error estimate


//? Embedded integrators


//! Return double !//


//? y = x


//it isn't clear whether al_bp_unregister is always called before or after al_bp_close,
//and sometimes it appears not to be called at all,
//even though one would expect the former to be always called and always before the latter,
//and the bp_ibr code follows that thought;
//thus, we modified bp_ibr_close to call bp_ibr_unregister if this wasn't called
//(and apparently bp_ibr_unregister doesn't throw any error if called (immediately?) after bp_ibr_close,
//but keep in mind that in such case dereferencing ibrHandle with 'ibrHandle->client' is undefined behavior,
//because ibrHandle's pointed data has already been deleted by bp_ibr_close with 'delete ibrHandle')


/*
 *  SyntaxError caused by eval exits Duktape/C function but destructors
 *  are executed.
 */


/*
 *  You can use C++ exceptions inside Duktape/C functions for your own
 *  purposes but you should catch them before they propagate to Duktape.
 */


/*
 *  If you let your own C++ exceptions propagate out of a Duktape/C function
 *  it will be caught by Duktape and considered a programming error.  Duktape
 *  will catch the exception and convert it to a Duktape error.
 *
 *  This may be allowed in a later version once all the implications have been
 *  worked out.
 */


/******************************************************************************
 *
 * \par Function Name:
 *      convert_bundle_from_dtn2_to_cgr
 *
 * \brief Convert the characteristics of the bundle from DTN2 to
 *        this CGR's implementation and initialize all the
 *        bundle fields used by the Unibo CGR.
 *
 *
 * \par Date Written:
 *      05/07/20
 *
 * \return int
 *
 * \retval  0  Success case
 * \retval -1  Arguments error
 * \retval -2 Bundle have a DTN name, not IPN. Can't use CGR.
 *
 * \param[in]    current_time       The current time, in differential time from reference_time
 * \param[in]    *Dtn2Bundle        The bundle in DTN2
 * \param[out]   *CgrBundle         The bundle in this CGR's implementation.
 *
 *
 * \par Revision History:
 *
 *  DD/MM/YY |  AUTHOR         |   DESCRIPTION
 *  -------- | --------------- | -----------------------------------------------
 *  05/07/20 | G. Gori		    |  Initial Implementation and documentation.
 *****************************************************************************/


/******************************************************************************
 *
 * \par Function Name:
 *      convert_routes_from_cgr_to_dtn2
 *
 * \brief Convert a list of routes from CGR's format to DTN2's format
 *
 *
 * \par Date Written:
 *      16/07/20
 *
 * \return int
 *
 * \retval   0  All routes converted
 * \retval  -1  CGR's contact points to NULL
 *
 * \param[in]     evc             Bundle's estimated volume consumption
 * \param[in]     cgrRoutes       The list of routes in CGR's format
 * \param[out]    *res        	 All the next hops that CGR found, separated by a single space
 *
 *
 * \par Revision History:
 *
 *  DD/MM/YY |  AUTHOR         |   DESCRIPTION
 *  -------- | --------------- | -----------------------------------------------
 *  16/07/20 | G. Gori         |  Initial Implementation and documentation.
 *****************************************************************************/


/******************************************************************************
 *
 * \par Function Name:
 *      add_contact
 *
 * \brief  Add a contact to the contacts graph of this CGR's implementation.
 *
 *
 * \par Date Written:
 *      02/07/20
 *
 * \return int
 *
 * \retval   1   Contact added
 * \retval   0   Contact's arguments error
 * \retval  -1   The contact overlaps with other contacts
 * \retval  -2   Can't read all info of the contact
 * \retval  -3   Can't read all info of the contact
 * \retval  -4   Can't read fromTime or toTime
 *
 * \param[in]   fileline	The line read from the file
 *
 *
 * \par Revision History:
 *
 *  DD/MM/YY |  AUTHOR         |   DESCRIPTION
 *  -------- | --------------- | -----------------------------------------------
 *  02/07/20 | G. Gori		    |  Initial Implementation and documentation.
 *****************************************************************************/


/******************************************************************************
 *
 * \par Function Name:
 *      add_range
 *
 * \brief  Add a range to the ranges graph of this CGR's implementation.
 *
 *
 * \par Date Written:
 *      02/07/20
 *
 * \return int
 *
 * \retval   1   Range added
 * \retval   0   Range's arguments error
 * \retval  -1   fileline is not properly formatted
 * \retval  -2   fileline doesn't start with "+"
 *
 * \param[in]  char*		The line that contains the range
 *
 *
 * \par Revision History:
 *
 *  DD/MM/YY |  AUTHOR         |   DESCRIPTION
 *  -------- | --------------- | -----------------------------------------------
 *  02/07/20 | G. Gori		    |  Initial Implementation and documentation.
 *****************************************************************************/


/******************************************************************************
 *
 * \par Function Name:
 *      read_file_contactranges
 *
 * \brief  Read and add all new contacts or ranges of the file with filename
 * 		  specified in the first parameter to the
 *         contacts graph of thic CGR's implementation.
 *
 * \details Only for Registration and Scheduled contacts.
 *
 *
 * \par Date Written:
 *      02/07/20
 *
 * \return int
 *
 * \retval  ">= 0"  Number of contacts added to the contacts graph
 * \retval     -1   open file error
 *
 * \param[in]   char*	The name of the file to read
 *
 * \par Revision History:
 *
 *  DD/MM/YY |  AUTHOR         |   DESCRIPTION
 *  -------- | --------------- | -----------------------------------------------
 *  02/07/20 | G. Gori         |  Initial Implementation and documentation.
 *****************************************************************************/


/******************************************************************************
 *
 * \par Function Name:
 *      update_contact_plan
 *
 * \brief
 *
 *
 * \par Date Written:
 *      01/07/20
 *
 * \return int
 *
 * \retval   0  Contact plan has been changed and updated
 * \retval  -1  Contact plan isn't changed
 * \retval  -2  File error
 *
 * \param[in]   filename     The name of the file from which we read contacts
 * \param[in]   update       Set true to update contact plan, false to not update
 *
 * \warning file should exist
 *
 * \par Revision History:
 *
 *  DD/MM/YY |  AUTHOR         |   DESCRIPTION
 *  -------- | --------------- | -----------------------------------------------
 *  01/07/20 | G. Gori         |  Initial Implementation and documentation.
 *****************************************************************************/


/******************************************************************************
 *
 * \par Function Name:
 *      exclude_neighbors
 *
 * \brief  Function that will exclude all the neighbors that can't be used as first hop
 *         to reach the destination. Currently it only clear the list.
 *
 *
 * \par Date Written:
 *      01/07/20
 *
 * \return int
 *
 * \retval   0   Success case: List converted
 *
 * \warning excludedNeighbors has to be previously initialized
 *
 * \par Notes:
 *           1. This function clear the previous excludedNeighbors list
 *
 * \par Revision History:
 *
 *  DD/MM/YY |  AUTHOR         |   DESCRIPTION
 *  -------- | --------------- | -----------------------------------------------
 *  01/07/20 | G. Gori         |  Initial Implementation and documentation.
 *****************************************************************************/


/******************************************************************************
 *
 * \par Function Name:
 *      callUniboCGR
 *
 * \brief  Entry point to call the CGR from DTN2, get the best routes to reach
 *         the destination for the bundle.
 *
 *
 * \par Date Written:
 *      05/07/20
 *
 * \return int
 *
 * \retval    0   Routes found and converted
 * \retval   -1   There aren't route to reach the destination
 * \retval   -3   Phase one arguments error
 * \retval   -4   CGR arguments error
 * \retval   -5   callCGR arguments error
 * \retval   -7   Bundle's conversion error
 * \retval   -8   Bundle's conversion error: bundle have DTN name instead of IPN
 *
 * \param[in]     time              The current time
 * \param[in]     *bundle           The DTN2's bundle that has to be forwarded
 * \param[out]    *res          	The list of best routes found written on a string separated by a space
 *
 *
 * \par Revision History:
 *
 *  DD/MM/YY |  AUTHOR         |   DESCRIPTION
 *  -------- | --------------- | -----------------------------------------------
 *  05/07/20 | G. Gori		    |  Initial Implementation and documentation.
 *****************************************************************************/


/******************************************************************************
 *
 * \par Function Name:
 *      computeApplicableBacklog
 *
 * \brief  Compute the applicable backlog (SABR 3.2.6.2 b) ) and the total backlog for a neighbor.
 *
 *
 * \par Date Written:
 *      20/07/20
 *
 * \return int
 *
 * \retval   0   Applicable and total backlog computed
 * \retval  -1   Arguments error
 *
 * \param[in]   neighbor                   The neighbor for which we want to compute
 *                                         the applicable and total backlog.
 * \param[in]   priority                   The bundle's cardinal priority
 * \param[in]   ordinal                    The bundle's ordinal priority (used with expedited cardinal priority)
 * \param[out]  *CgrApplicableBacklog      The applicable backlog computed
 * \param[out]  *CgrTotalBacklog           The total backlog computed
 *
 * \par Notes:
 *          1. This function talks with the CL queue, that should be done during
 *             phase two to get a more accurate applicable (and total) backlog
 *
 * \par Revision History:
 *
 *  DD/MM/YY |  AUTHOR         |   DESCRIPTION
 *  -------- | --------------- | -----------------------------------------------
 *  20/07/20 | G. Gori         |  Initial Implementation and documentation.
 *  10/08/20 | G. Gori		   |  Fixed oasys::Lock bug
 *****************************************************************************/


/******************************************************************************
 *
 * \par Function Name:
 *      destroy_contact_graph_routing
 *
 * \brief  Deallocate all the memory used by the CGR.
 *
 *
 * \par Date Written:
 *      14/07/20
 *
 * \return  void
 *
 * \param[in]  time  The current time
 *
 *
 * \par Revision History:
 *
 *  DD/MM/YY |  AUTHOR         |   DESCRIPTION
 *  -------- | --------------- | -----------------------------------------------
 *  14/07/20 | G. Gori		    |  Initial Implementation and documentation.
 *****************************************************************************/


/******************************************************************************
 *
 * \par Function Name:
 *      initialize_contact_graph_routing
 *
 * \brief  Initialize all the data used by the CGR.
 *
 *
 * \par Date Written:
 *      01/07/20
 *
 * \return int
 *
 * \retval   1   Success case: CGR initialized
 * \retval  -1   Error case: ownNode can't be 0
 * \retval  -2   can't open or read file with contacts
 * \retval  -3   Error case: log directory can't be opened
 * \retval  -4   Error case: log file can't be opened
 * \retval  -5   Arguments error
 *
 * \param[in]   ownNode   The node that the CGR will consider as contacts graph's root
 * \param[in]   time      The reference unix time (time 0 for the CGR)
 *
 * \par Revision History:
 *
 *  DD/MM/YY |  AUTHOR         |   DESCRIPTION
 *  -------- | --------------- | -----------------------------------------------
 *  01/07/20 | G. Gori         |  Initial Implementation and documentation.
 *****************************************************************************/


// HEALPix like equal-area isolatitude tessellations of the sphere with N_theta = 3


// union vector with spherical coordinates


// Stokes vector changes
// spherical trigonometry is used


// distance to plane in plane normal length units


// Nodes for the grid


// Elements of the grid


// calculate smax -- maximum distance photon can travel *******


// NEED TO BE REDONE


// Compute V(q,r) values based on BFN1988 sections 2.3 and 3.3.


// We use algorithm described in Bratley, Fox, Niederreiter, ACM Trans. Model. Comp. Sim. 2, 195 (1992) - BFN1988
// We use Niederreiter base 2 sequence, hence we need only 1 bit to store polynomial coefficients
// Moreover, ADD and MUL operations for this coefficient are bitwise XOR and AND respectively


/*!
    @brief scan a number literal

    This function scans a string according to Sect. 6 of RFC 8259.

    The function is realized with a deterministic finite state machine derived
    from the grammar described in RFC 8259. Starting in state "init", the
    input is read and used to determined the next state. Only state "done"
    accepts the number. State "error" is a trap state to model errors. In the
    table below, "anything" means any character but the ones listed before.

    state    | 0        | 1-9      | e E      | +       | -       | .        | anything
    ---------|----------|----------|----------|---------|---------|----------|-----------
    init     | zero     | any1     | [error]  | [error] | minus   | [error]  | [error]
    minus    | zero     | any1     | [error]  | [error] | [error] | [error]  | [error]
    zero     | done     | done     | exponent | done    | done    | decimal1 | done
    any1     | any1     | any1     | exponent | done    | done    | decimal1 | done
    decimal1 | decimal2 | decimal2 | [error]  | [error] | [error] | [error]  | [error]
    decimal2 | decimal2 | decimal2 | exponent | done    | done    | done     | done
    exponent | any2     | any2     | [error]  | sign    | sign    | [error]  | [error]
    sign     | any2     | any2     | [error]  | [error] | [error] | [error]  | [error]
    any2     | any2     | any2     | done     | done    | done    | done     | done

    The state machine is realized with one label per state (prefixed with
    "scan_number_") and `goto` statements between them. The state machine
    contains cycles, but any cycle can be left when EOF is read. Therefore,
    the function is guaranteed to terminate.

    During scanning, the read bytes are stored in token_buffer. This string is
    then converted to a signed integer, an unsigned integer, or a
    floating-point number.

    @return token_type::value_unsigned, token_type::value_integer, or
            token_type::value_float if number could be successfully scanned,
            token_type::parse_error otherwise

    @note The scanner is independent of the current locale. Internally, the
          locale's decimal point is used instead of `.` to work with the
          locale-dependent converters.
    */


/*!
    @brief Reads in a BSON-object and passes it to the SAX-parser.
    @return whether a valid BSON-value was passed to the SAX parser
    */


/*!
    @brief Read a BSON document element of the given @a element_type.
    @param[in] element_type The BSON element type, c.f. http://bsonspec.org/spec.html
    @param[in] element_type_parse_position The position in the input stream,
               where the `element_type` was read.
    @warning Not all BSON element types are supported yet. An unsupported
             @a element_type will give rise to a parse_error.114:
             Unsupported BSON record type 0x...
    @return whether a valid BSON-object/array was passed to the SAX parser
    */


/*!
    @brief Reads an array from the BSON input and passes it to the SAX-parser.
    @return whether a valid BSON-array was passed to the SAX parser
    */


/*!
    @param[in] get_char  whether a new character should be retrieved from the
                         input (true) or whether the last read character should
                         be considered instead (false)
    @param[in] tag_handler how CBOR tags should be treated

    @return whether a valid CBOR value was passed to the SAX parser
    */


/*!
    @return whether a valid MessagePack value was passed to the SAX parser
    */


/*!
    @param[in] format   the current format
    @param[in] detail   a detailed error message
    @param[in] context  further context information
    @return a message string to use in the parse_error exceptions
    */


/*!
    @brief public parser interface

    @param[in] strict      whether to expect the last token to be EOF
    @param[in,out] result  parsed JSON value

    @throw parse_error.101 in case of an unexpected token
    @throw parse_error.102 if to_unicode fails or surrogate error
    @throw parse_error.103 if to_unicode fails
    */


/*!
    @brief split the string input to reference tokens

    @note This function is only called by the json_pointer constructor.
          All exceptions below are documented there.

    @throw parse_error.107  if the pointer is not empty or begins with '/'
    @throw parse_error.108  if character '~' is not followed by '0' or '1'
    */


// can't use conversion operator because of ambiguity


/*!
    @param[in] j  JSON value to serialize
    @pre       j.type() == value_t::object
    */


/*!
    @param[in] j  JSON value to serialize
    */


/*!
    @param[in] j  JSON value to serialize
    @param[in] use_count   whether to use '#' prefixes (optimized format)
    @param[in] use_type    whether to use '$' prefixes (optimized format)
    @param[in] add_prefix  whether prefixes need to be used for this value
    @param[in] use_bjdata  whether write in BJData format, default is false
    */


/*!
    @return The size of a BSON document entry header, including the id marker
            and the entry name size (and its null-terminator).
    */


/*!
    @brief Writes a BSON element with key @a name and double value @a value
    */


/*!
    @brief Writes a BSON element with key @a name and string value @a value
    */


/*!
    @brief Writes a BSON element with key @a name and integer @a value
    */


/*!
    @brief Writes a BSON element with key @a name and unsigned @a value
    */


/*!
    @return The size of the BSON-encoded array @a value
    */


/*!
    @brief Writes a BSON element with key @a name and array @a value
    */


/*!
    @brief Writes a BSON element with key @a name and binary value @a value
    */


/*!
    @brief Calculates the size necessary to serialize the JSON value @a j with its @a name
    @return The calculated size for the BSON document entry for @a j with the given @a name.
    */


/*!
    @brief Serializes the JSON value @a j to BSON and associates it with the
           key @a name.
    @param name The name to associate with the JSON entity @a j within the
                current BSON document
    */


/*!
    @brief Calculates the size of the BSON serialization of the given
           JSON-object @a j.
    @param[in] value  JSON value to serialize
    @pre       value.type() == value_t::object
    */


/*!
    @param[in] value  JSON value to serialize
    @pre       value.type() == value_t::object
    */


/*!
    @brief determine the type prefix of container values
    */


/*!
    @return false if the object is successfully converted to a bjdata ndarray, true if the type or size is invalid
    */


/*!
Generates V = buffer * 10^decimal_exponent, such that M- <= V <= M+.
M- and M+ must be normalized and share the same exponent -60 <= e <= -32.
*/


/*!
    @brief internal implementation of the serialization function

    This function is called by the public member function dump and organizes
    the serialization internally. The indentation level is propagated as
    additional parameter. In case of arrays and objects, the function is
    called recursively.

    - strings and object keys are escaped using `escape_string()`
    - integer numbers are converted implicitly via `operator<<`
    - floating-point numbers are converted to a string using `"%g"` format
    - binary values are serialized as objects containing the subtype and the
      byte array

    @param[in] val               value to serialize
    @param[in] pretty_print      whether the output shall be pretty-printed
    @param[in] ensure_ascii If @a ensure_ascii is true, all non-ASCII characters
    in the output are escaped with `\uXXXX` sequences, and the result consists
    of ASCII characters only.
    @param[in] indent_step       the indent level
    @param[in] current_indent    the current indent level (only used internally)
    */


/*!
     * @brief convert a byte to a uppercase hex representation
     * @param[in] byte byte to represent
     * @return representation ("00".."FF")
     */


/*!
    @brief check whether a string is UTF-8 encoded

    The function checks each byte of a string whether it is UTF-8 encoded. The
    result of the check is stored in the @a state parameter. The function must
    be called initially with state 0 (accept). State 1 means the string must
    be rejected, because the current byte is not allowed. If the string is
    completely processed, but the state is non-zero, the string ended
    prematurely; that is, the last byte indicated more bytes should have
    followed.

    @param[in,out] state  the state of the decoding
    @param[in,out] codep  codepoint (valid only if resulting state is UTF8_ACCEPT)
    @param[in] byte       next byte to decode
    @return               new state

    @note The function has been edited: a std::array is used.

    @copyright Copyright (c) 2008-2009 Bjoern Hoehrmann <bjoern@hoehrmann.de>
    @sa http://bjoern.hoehrmann.de/utf-8/decoder/dfa/
    */


/*
     * Helper function for dump_integer
     *
     * This function takes a negative signed integer and returns its absolute
     * value as unsigned integer. The plus/minus shuffling is necessary as we can
     * not directly remove the sign of an arbitrary signed integer as the
     * absolute values of INT_MIN and INT_MAX are usually not the same. See
     * #1708 for details.
     */


/// constructor for empty values of a given type


/// @brief checks whether the container is empty.
/// @sa https://json.nlohmann.me/api/basic_json/empty/


// Note: The type after -> is weird, because VS2015 cannot parse
//       the expression used in the typedef inside, when it is in
//       return type. Yeah.


// This is the general overload that takes a any string matcher
// There is another overload, in catch_assertionhandler.h/.cpp, that only takes a string and infers
// the Equals matcher (so the header does not mention matchers)


// Only populated if resultType is an error


// Returns true if the current process is being debugged (either
// running under the debugger or has a debugger attached post facto).


// The standard POSIX way of detecting a debugger is to attempt to
// ptrace() the process, but this needs to be done from a child and not
// this process itself to still allow attaching to this process later
// if wanted, so is rather heavy. Under Linux we have the PID of the
// "debugger" (which doesn't need to be gdb, of course, it could also
// be strace, for example) in /proc/$PID/status, so just get it from
// there instead.


// Extracts the actual name part of an enum instance
// In other words, it returns the Blue part of Bikeshed::Colour::Blue


// For MSVC, we reserve part of the stack memory for handling
// memory overflow structured exception.


// namespace Catch
// end catch_matchers_floating.cpp
// start catch_matchers_generic.cpp


// Safe rotr implementation thanks to John Regehr


// Used for copy state/ flags from


// end unnamed namespace


// Two of the processing methods return true to signal the caller to return
// without adding the given character to the current pattern strings


//// ======================================================= ////
//
//   Out-of-line defs for full specialization of StringMaker
//
//// ======================================================= ////


// Colour, message variants:
// - white: No tests ran.
// -   red: Failed [both/all] N test cases, failed [both/all] M assertions.
// - white: Passed [both/all] N test cases (no assertions).
// -   red: Failed N tests cases, failed M assertions.
// - green: Passed [both/all] N tests cases with M assertions.


// if string has a : in first line will set indent to follow it on
// subsequent lines


// Formats the duration in seconds to 3 decimal places.
// This is done because some genius defined Maven Surefire schema
// in a way that only accepts 3 decimal places, and tools like
// Jenkins use that schema for validation JUnit reporter output.


// The return value indicates if the messages buffer should be cleared:


/*!
  See main page of documentation for description of file format
  \param[in] paramfilename Name of file to read from
  \param[in] silent Don't print status text if if verbose is set in
    param file
*/