README file for the TBCI Numerical Library
==========================================
Kurt Garloff <kurt@garloff.de>, last updated for numlib-2.3.0
$Id: README,v 1.28.2.20 2019/05/29 10:47:59 garloff Exp $


here is our Numerical Library. It contains classes to store objects like
Cplx numbers, Vectors, etc. and some functions to deal with them, eg.
solvers. It's written in C++ and templated.
It is called TBCI library, because the Temporary Base Class Idiom is used 
to prevent bad performance commonly seen with object oriented designs.

This document should give you a short introduction and an overview.


Directories:
------------
* lina:  Contains the classes and solvers
* utils: Some useful tiny programs
* bench: A little benchmark used to profile the library and to 
         compare different systems
* doc:   A document which explains the ideas of TBCI and provides
         some details about the classes. 
	 (See also section doxygen below for documentation.)
* back_up: Nomen est Omen

There are subdirectories. The common structure is to use
include/ for headers, source/ for C(++) files, test/ for (little)
testing programs and bin-<ARCH>/ for objects and binaries.
(<ARCH> is replaced by something like alpha, ix86, ...)


Features:
---------
* C++ [1]
* Templated
* Temporary Base Class Idiom for Vectors and Matrices [2]
* Optional error checking (compile time switch)
* Optional exception handling (dito)
* Namespace support (optional, default for compilers since ~2001)
* Multithreading (POSIX threads) for some routines on Shared Mem 
  architectures
* Lapack and SuperLU interfaces
* Doxygen documentation (not yet complete)


Classes: (all in namespace TBCI::)
--------
cplx
BVector, Vector
Matrix
BdMatrix, Symm_BdMatrix, CRMatrix, CSCMatrix
 + Fortran versions of some of these Matrices
Tensor
list (double linked list)

plus some helper classes


Solvers:
--------
Gauss-Jordan, LU and LU optimized for BdMatrix [3]
Expon. Expand., Quasi-Minimal Residual, Generalized Minimum Residual,
Iterative Refinement (Preconditioned Richardson), Chebyshev,
Conjugate Gradient (CG), CG squared, BiCG, BiCG stabilized [4]

Preconditioner: Diagonal (Jacobi) Preconditioner, Incomplete LU 
(ILU-0, D-ILU)

SuperLU interface


How to build:
-------------
This library was first developed with the gcc-2.7.2.x Compiler 
under Linux.
Later on 2.7.2p had to be used and then egcs-1.0.x and gcc-2.8.x.
The switch to egcs-1.1.x was done.
gcc-2.95.x used NOT to work due to some C++ bugs. Some of them have been
fixed in the 2.96 snapshots and some more are being worked on, so there is
hope that gcc-2.96 can compile this library, when it will be released.
There have been found a number of workarounds, now, that make a compilation
with 2.95.2 possible. Please read README.gcc295 for details.
With gcc-3.x, these problems are history.

This is of course historic -- you can build the library with gcc-4.x and
newer (tests are performed with 4.8 thr 9.x), icc, clang, ...

Some parts of this library are used by colleagues under Win32 with 
MS VC++ 5/6. These parts have been fixed to work with VC++.
Some parts have not, and the main issue seems to be the nonstandard
behaviour of VC++ for variable declarations in loop headers.

The code has been equipped with the necessary ifdefs to support various
compilers, amongst which egcs-1.1.2, gcc-2.95.x, gcc-3.0.x, Compaq cxx
(6.3.3.8), intel C++ (5.01), MIPSpro (7.3.1.2m) and MS VC 6 (SP4/5).

The following assumes you use a Un*x/Linux system. The library has been 
tested with Linux/x86, Linux/Alpha, Linux/PPC, Linux/SPARC, Linux/S390,
Linux/iA64 and Digital Unix 4.0x and SGI IRIX.

You need:
GNU make (tested: 3.76.1), egcs(tested: 1.1.x)/gcc(2.95.x or 3.0.x) incl.
libstdc++, sed (tested: 2.x and 3.0), grep (any should do), GNU tar (1.12),
gzip/bzip2. 
Some more standard Un*x tools: ls, rm, cat, echo, cp, mv, ln, ...
Any text editor.
Bourne shell. Probably, the scripts contain some bashisms, so you need 
bash (tested: 1.14.x and 2.0x).
LaTeX to process the documentation (preferably tetex ...)

Useful:
GNU diffutils, patch, CVS
Integr. Development Env. (kdevelop, wipeout, ...)
bibtex, xdvi, dvips, psutils, ghostscript, gv, acroread
doxygen, graphviz

For using the LAPACK and the SUPER_LU interfaces, you need to have f2c,
f2clibs, (c)lapack and superlu. Fetch them from ftp.netlib.org:

ftp://ftp.netlib.org/clapack/clapack.tgz
ftp://ftp.netlib.org/scalapack/prototype/superlu_1.1.tgz
ftp://ftp.netlib.org/f2c/src/*

Note: The f2c libs and BLAS are included in the clapack.tgz package.
These packages are mirrored on our server:
http://pebbles.e-technik.uni-dortmund.de/numlib/numlib/

For using the library, just add the lina/include directory to your path
and include the headers needed. For example apps, see bench/libbench.cc
and the programs in lina/test/.
You may want to have SMP support. In this case, you also need to link
against lina/bin-<ARCH>/smp.po and -lpthread -lrt (on Linux).

There are Makefiles in almost any directory. To use them just type make
(or gmake, if this is the name of your GNU make). Here is an overview of
what will be made:
(a) lina: The libraries libtbcidouble.so, libtbcicplxdouble.so and
    libtbcistdcomplexdouble.so which contain instantiations of most 
    classes. This allows you to save some time building your apps with
    -fno-implicit-templates and link against the lib. Unfortunately, 
    it does not save that much time, as a lot of functions are inlined
    for (runtime) performance reasons. You may also build static 
    libraries by specifying the target static.
    Building the libraries provides a good test for the library 
    implementation, as almost everything is instantiated and therefore
    checked by the compiler.
    Note that you don't actually need this library, because all classes 
    are templated and instantiated when needed by the compiler unless 
    you use -fno-implicit-templates or -fexternal-templates or -frepo
    to save compile time.
    If you use SMP support (so don't compile with NO_SMP=1) you need to
    link against the smp helpers; these are part of libtbcidouble, 
    cplxdouble, and stdcomplexdouble but also available separately
    in libtbcismp.so.
    There are also a few more libraries: 
    libtbcispecfun.so provides a few special functions.
    libtbcilapack.so provides an interface to the Lapack library with
    a wrapper for eigenvalue calculation (for TBCI::F_Matrix).
    libtbcisuperlu.so provides an interface to the SuperLU solver
    (for TBCI::CSCMatrix).
(b) bench: The benchmark binaries are built.
(c) doc: The doc.tex will be processed by latex to result in doc.dvi. 
    Optionally, a .ps, .ps2, .pdf, .pdf2 file will be built.
(d) utils: The utils will be built. A very important one of which is 
    the auto_decl binary, which creates the _gd and _inst files
    automatically by parsing your classes and friend declarations.
(e) back_up: Backup files of the current code are made.
(f) lina/test will not be built by default.
    It contains little test programs, which can be used as examples
    and to validate the correctness of the library.

There is something to be build in order to test the library:
The libbench benchmark in the bench directory. Just type (g)make there.

All Makefiles include numerix/Make.Std which includes numerix/Make.Sys.
Common flags go here.


Build instructions for the library:
-----------------------------------
Go to the lina directory and do

./autogen.sh
(It calls libtoolize, autoheader, aclocal, automake, and autoconf.)

Sidenote: libtool is not really required and is subsequently not used
in the compilation. If autogen.sh does not find libtool on your system
it will patch configure.in and lib/Makefile.am trying to make automake
succeed anyway.

Call ./configure. (If you omit this, make will take care of it.)
Now you can build the library with make in the lina dir or you can build
all programs and docu (including the library) by typing make in the
main numerix-2.0 directory.


Makefile flags:
---------------
The following flags can be specified on the make command line, i.e.
make <FLAGS> <OVERRIDES> <TARGETS>. Defaults are marked with a *

FLAGS:

* Error checking:
 ERRCHECK=1:	 Check for bounds, 0 division and other error conditions with
		 the BCHK macro
 BOUNDCHECK=1:	 historical alias for ERRCHECK
	(the following two options are only useful in conjunction with 
	 ERRCHECK=1)
 NO_EXCEPT=1:	 Don't throw exceptions, but instead use cerr error reporting
		 (and optionally abort(), see next flag)
 ABORT_ON_ERR=1: abort() in case of errors
* Language features
 NO_NS_TBCI=1 :	 Don't use namespaces
		 Default is to put the lib into the ::TBCI:: namespace.
 NO_NS=1	 Completely switch off namespaces (will break on conformant
		 compilers, as some functions are in std::)
* Optimization
 OPT=1:		 Use additional optimization flags
 OPT_ARCH=1:	 Architecture specific optimizations (breaking otherwise
		 compatible machines)
 OPT_GENERIC=1:  Pass flags to compiler to tune for generic platform.
 OMITFP=1:	 Use -fomit-frame-pointer compiler flag
 OPT_SSA=1:	 Use gcc-3 SSA transformation and dead code elimination
 PREFER_COPY=1:  Return a copy instead of a const ref in const access ops ()
* Other features
 DEBUG=1:	 Use debugging flags (-g)
 NOSMP=1:	 Don't build multithreaded code (based on pthreads)
 DEBUG_THREAD=1: Used for thread debugging
 NO_AUTOCONF=1:  Build without automatic compiler feature tests.
		 Needed in case you don't have all the available tools
		 (aclocal, autoheader, automake and autoconf) or in case
		 the configu_manual actually is better than the
		 configure.in tests.
 NEW_BRACKET=1:  Speeds up element access with [][] for Matrices.
 		 However, Matrix::operator[] does not yield a valid
		 Vector any longer.

You can pass additional flags to the compiler by
 EXTRA_CFLAGS=<ADDITIONAL COMPILER FLAGS>
 EXTRA_LFLAGS=<ADDITIONAL LINKER FLAGS>
or override the normal ones by
 CFLAGS=<Compiler flags>
 LFLAGS=<Linker flags>

You can give additional options for single target by specifying
 CFLAGS_<TARGET>=<Additional flags>

There are some preprocessor defines which can be used for performance tuning
or for modifying error behaviour (NOSMP_XXX, BDMATVEC_XXX, PREFER_XXX, ...)
with EXTRA_CFLAGS="-Ddefine". Check the sources, espedially config_manual.h
and basics.h

By default, the names and flags are chosen to be suitable for egcs. It 
is assumed, that is is invoked by gcc resp. g++. It can be overriden
by 
CC=<C-COMPILER>     default: gcc
CXX=<C++-COMPILER>           g++
AR=<AR-BINARY>               ar
ARFLAGS=<FLAGS>              -rs
SAR=<SHARED_ARCHIVER>        $(CC) -shared
LD=<LINKER>                  $(CC)
LXX=<C++-LINKER>             $(CXX)

The name of a lot of extra binaries can be specified. See Make.Std for a
list. 

Normally, there exists a target with the name default, shared, static and
clean. You may also specify the name of the target file.


Autoconf
--------
Instead of using the results of the tests from configure.in, you may 
also use hardcoded knowledge about the C++ compilers collected in
config_manual.h. This can be switched on by passing NO_AUTOCONF=1 to make.
As of version 2.3.0, the tests should be complete to allow compilation on
various platforms with various compilers. If you want to compile optimized
code, you may still have the possibility to improve speed by specifying 
special compiler flags, though.
At this moment, the configure script is not yet distributed; you need
automake, autoheader, aclocal and autoconf to create it; the makefile will
take care of it. Optionally you can libtoolize it. 
Note that the autoconf/configure generated Makefile at this moment won't
work: It misses the auto_decl step which produces the guiding declarations
(needed for g++) and instatiation lists (needed in case you want to build a
library). 

Usage
-----
#include <tbci/vector.h>
#include <iostream>
// Avoid the need to link with smp.po
namespace TBCI { unsigned int tbci_control = _TBCI_CWD_DEFAULT; };
using namespace TBCI;
int main()
{
  Vector<double> a(5), b(5);
  a(1) = -5.2; b(3) = 1.7;
  Vector<double> c(a+b);
  std::cout << "a+b = " << c << std::endl;
  std::cout << "2.1*a-b = " << 2.1*a-b << std::endl;
  // Out of bound - triggers exception if compiled with -DTBCI_EXPCHECK
  std::cout << "c(5) = " << c(5) << std::endl;
  return 0;
}

Notes:
- Compile with g++ -O2 (and pass include path as necessary)
- With an installed libtbci, you might rather pass -DHAVE_TBCICONFIG_H and
  use the determined systems/compiler config than the heuristics in
  config_manual.h. You'll have noted the warning.
- You could compile with -fno-implicit-templates (to save code size and
  compile time) and link against the precompiled library.
- You will need to compile smp.cc and link against it for multithreading
  or link against the precompiled library (-ltbcidouble) or -- if you
  don't want multithreading -- include the TBCI::tbci_control global
  variable in one of your objects (see above) to avoid linker errors.
- You can also switch off error checking -DTCBI_NO_ERRCHECK completely
  and then don't need the global variable - not recommended.
- For development, it's recommended to instead enable -DTBCI_EXPCHECK:
  Enable expensive error checking, can be runtime-disabled with
  enable_expcheck(false); but will still create some branches ...
- If you want multithreading, use TBCI::init_threads() and free_threads()
  from smp.cc or -ltbcidouble. See e.g. bench/libbench_double.cc as
  an example.


Doxygen
-------
We recently started to use doxygen to generate the detailed documentation 
of the classes, variables, namespaces, files ...
Get doxygen from http://www.stack.nl/~dimitri/doxygen/
Documentation gets produced in the doxygen subdirectories when you call
doxygen in one of the subdirectories which have a Doxyfile.
make dox from the main directory will also do ...
Doxygen packages are also available as part of the SuSE Linux distribution
(guess why ;-). Installing dot from the graphviz package (AT&T) is also
useful to get graphs of inheritance etc.
ftp://ftp.suse.com/pub/people/garloff/linux/graphviz/


Copyright:
----------
This code is free software. It is protected by the GNU LGPL v2.
You can use the code under the conditions of GNU LGPL v2 or later
versions.
See file COPYING.LIB for details. 
This has been changed in 2002: All the contributors agreed on 
prefering the LGPL over the GPL for this project. (The library was
under GNU GPL v2 before.)
Disclaimer: Please be aware of the fact, that the authors hope, that 
this library may be useful, but that they don't take any warranty
for that. No liability for causing damage is granted. Please read
No. 11 and 12 of the GNU LGPL for details.

The LGPL grants you the right to use the library in your own projects. Those
do not need to be open-source projects. However, if you change the library,
you need to release your modifications to the library in case you release
any code using it. See the LGPL for details again.
We would strongly appreciate to get a notice from you when you use TBCI in
one of your projects. We would also appreciate if you credit the authors of
TBCI in your project.

The GNU LGPL does not apply to the files in the directories visual/, mpt/,
grid/, grids/ and pssi/ (and these are not distributed along with TBCI
either normally). Those are not free but copyrighted by the authors
and not freely distributable.

In interface/specfun/, you will find some useful routines, which were NOT
written by us. Those files were distributed freely, but the licensing
of them is not always completely clear. We believe that they have been
offered for free to the public domain, because the authors wanted to do so.
As such they can be integrated in our library and used under LGPL terms. 
We take no responsibility for this, though, if this turns out to be an 
error.


How to get it:
--------------
Download it from 
http://plasimo.phys.tue.nl/TBCI/

You will also find a link to this page from my personal numerics page:
http://www.garloff.de/kurt/numerix/

There is also a mailing list. Send a subscribe request to
 <numerix-request@plasimo.phys.tue.nl>
and mails to
 TBCI-List <numerix@plasimo.phys.tue.nl>

From time to time, there will be updates on the library, which will be
announced in this list.


Patches:
--------
You found a bug and wnat to report it? You have good ideas on how to
improve the library? You want to help the development? 
YOU ARE VERY WELCOME!

But ... please be aware of some technical issues.

If you change something and just send the new file to us, we won't be able 
to accept it! Why?
Because several people work on the sources and it is very likely, that
overwriting our files with your changed file will discard the work of other
people done at the same time. This is unacceptable.

So please, before making any changes, backup the old file (e.g. by just 
copying it: cp -p file.h file.h.orig, or by copying a hole tree), do your 
changes, test them and send a unified diff, i.e. the output of 
diff -up file.h.orig file.h.
This diff can be applied by us with the patch program without discarding the
work of anybody.

If you ever followed development of open source projects, you should be very
familiar with that procedure.

If you want to work a lot on the files, we may grant you read-write CVS-
access, which we use internally.

Please send these diffs, ideas, bug-reports etc. to the TBCI-list and
optionally CC: to me.


TO DO:
------
You may want to know, what can be done?
Please read TODO file!


References:
-----------
[1] Bjarne Stroustrup: The C++ Programming language, 3rd ed., Addison-Wesley,
   1997
[2] K. Spanderen, Y. Xylander: Gut kalkuliert. Effiziente Numerik mit C++,
   iX 11/96: 166-173, Verlag Heinz Heise, Hannover, FRG
[3] W.H. Press et. al.: Numerical Recipes in C, Cambridge University Press, 
    2nd ed., 1992
[4] R. Barret et. al.: Templates for the Solution of Linear Systems: Building
    Blocks for Iterative Methods, Society for Industrial and Applied 
    Mathematics (SIAM), Philadelphia, 1994
    ftp://netlib2.cs.utk.edu/linalg/templates2.tar
[5] http://etude.uwaterloo.ca/Ae/
[6] Kevin Dowd & Charles Severance: High Performance Computing, 2nd edition,
    O'Reilly, 1998

Trademarks:
-----------
Some names in this document or in other files of this library may be 
Registered Trademarks of their owners. 


Acknowledgements:
-----------------
A lot of people have made major contributions to the code. I will just name
a few of them: 

Attila M. Bilgic
Andreas Ahland
Jens Lenge
Joern Kastner
Jose L Tinoco
and some more people which I forgot.

They all work or worked together with me at the Department for 
High Frequency Engineering (Prof. Dr.-Ing. E. Voges) at the 
University of Dortmund (Germany).
Please visit the web pages:
http://www.hft.e-technik.uni-dortmund.de/

The development of the library was continued during my tenure at
Eindhoven University of Technology (TU/e) and I'm grateful to the
resaerch groups ETP (now P&MP) and EPG there.
http://www.etp.phys.tue.nl/
http://www.phys.tue.nl/EPG/

Significant contributions were made from
Jan van Dijk
Bart Hartgers
and others at TU/e.
                                                                     KG
