Coder Social home page Coder Social logo

r3brootgroup / r3broot Goto Github PK

View Code? Open in Web Editor NEW
18.0 22.0 101.0 115.35 MB

Framework for Simulations and Data Analysis of R3B Experiment

Home Page: https://github.com/R3BRootGroup/R3BRoot/wiki

License: GNU General Public License v3.0

CMake 1.91% Shell 0.25% C++ 74.93% GLSL 0.06% Perl 0.07% C 20.30% Hack 0.25% Fortran 2.12% Python 0.10% Makefile 0.02%
nuclear-physics simulation data-analysis nuclear-reactions fair-centre r3b nustar cplusplus geant4 c

r3broot's Introduction

R3BRoot Software license

CI-CD Static Analysis Validate Codemeta Cleanup Caches on PR Close

The R3BRoot Framework

The R3BRoot software is based on the FairRoot framework and can be used to perform Monte Carlo simulations and experimental data analysis of the R3B (Reactions with Relativistic Radioactive Beams) nuclear physics experiments at the GSI-FAIR research center (Facility for Antiproton and Ion Research). The user can create simulated data and/or perform analysis with the same framework. Geant3 and Geant4 transport engines are supported, however, the implemented tasks that create simulated data do not depend on a particular Monte Carlo engine. The framework delivers base classes which enable the users to construct their detectors and/or analysis tasks in a simple way, it also delivers some general functionality like track visualization. Moreover, an interface for reading experimental and/or simulated magnetic field maps is also implemented.

Discussion Forum

For the software-related user support you can post a new topic on our forum.

License

R3BRoot is distributed under the terms of the GNU General Public Licence version 3 (GPLv3).

Release Information

Please visit releases

Download

git clone https://github.com/R3BRootGroup/R3BRoot.git
cd R3BRoot
git clone https://github.com/R3BRootGroup/macros.git

Step by Step Installation

Required Software

First, you will need to install FairSoft and FairRoot. For more details:

  1. Install FairSoft

  2. Install FairRoot

Configure and Compile

export SIMPATH=%PATH_TO_FAIRSOFT%
export FAIRROOTPATH=%PATH_TO_FAIRROOT%
# from %R3BRoot_DIRECTORY%
mkdir build
cmake -S . -B ./build
cmake --build ./build
source build/config.sh

To run the detector tests do:

 # In the same shell from %R3BRoot_DIRECTORY%:
cd build
ctest --parallel ${number_of_threads}

Simulations and Data Analysis

This is performed from the GitHub parameter and data analysis repository, which contains all the macros and parameter files needed by the user to carry out the simulations and data analysis of each experiment. There is one repository per experiment, please, visit the R3B-Wiki for more details.

Contributing

Please ask your questions, request features, and report issues by creating a github issue.

Code Formatting

The R3BRoot project uses clang-format-15 to ensure a common code formatting. The script "clang-format-all.sh" can be used for this purpose:

source util/clang-format-all.sh

More Information

r3broot's People

Contributors

akelic avatar andrealagni avatar antia1996 avatar audreychatillon avatar bl0x avatar christiantackegsi avatar eleonora0412 avatar gabrigarjim avatar hapol avatar igasparic avatar inkdot7 avatar isyndikus avatar janmayer avatar jose-luis-rs avatar jtscheuschner avatar klenze avatar kresan avatar malabi avatar manuelxarepe avatar martinafeijoo avatar michael-heil avatar miharenthas avatar mwhiteheadyork avatar nmozumdar avatar pablocabanelas avatar rplag avatar ryotani avatar sonjastorck avatar vadimr3b avatar yanzhaow avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

r3broot's Issues

Preview: Rethinking Histogram filling

(This is a kinda follow-up to #436.)

To add a histogram to a FairTask, the following steps are normally needed:

  • Add the Hist-Pointer as a class member
  • In the constructor, create the histogram specifying
    • name, title,
    • (per Axis): binning, min, max,
    • (optionally) labels for each Axis
  • In the Exec method, a cascade of for loops iterates over the various TCA entries the histogram depends on, possibly tests for some cuts and calls hist->Fill(...)
  • (optionally) have a way to disable expensive histograms when they are not needed
  • (optionally) if the histograms are to be written out explicitly (e.g. in FinishTask), it would be useful to store them all in a std::vector or something.

For one or two histograms, this does not seem to bad, but typically, we have many more: R3BCalifaOnlineSpectra, for example, uses 25 different hist pointers. Ten of these are (possibly multi-dimensional) C-Arrays of pointers, adding up to four layers of for loops (plus highly questionable sprintfs) around their constructor calls. In our old go4 processor, we also had the functionality to selectively disable histograms, resulting in #ifdefs in three different places per histogram.

As part of my popular "avoid working directly on my PhD" project, I have created some basic infrastructure for a better way of histogram management.

The basic idea is to have the abstraction called Axis for some quantity. It includes:

  • binning
  • range
  • axis label
  • which r3bdata types are needed to calculate it
  • the formula to calculate it from these.

Each axis definition is stored as a type.

An autofill histogram is now defined by using

  • a counter type (e.g. int, float, double. No uint64_t, because ROOT.)
  • an AxisList, containing at least a x axis, and possibly a y axis and a weight axis
  • a name/title

When the AutoFill method of this thing is called, it will iterate over the Cartesian product over all available event values (as per Container<dataname>) of the types given by the multiset-union of its axis dependencies, and call each axis formula lambda with exaclty its required parameters.

In my current analysis class, I have a fairtask with a header containing:

protected:
  std::vector<AutoFillHistBase* > hists{};
public:
  void Exec(Option_t* option) override
  {
    for (auto& h: hists)
      h->AutoFill();
  }

All the magic of what histograms are defined happens in the constructor (in the cxx):

  using a_en_lab=Axis<1000, 0, 10000,  STR("E_{Lab} in keV"), GETTER(GetEnergyDeposit), R3BCalifaClusterData>;
  hists.push_back(new AutoFillHist<int, AxisList<a_en_lab> >("en_lab"));
  // pointless but valid:
  hists.push_back(new AutoFillHist<int, AxisList<a_en_lab, a_en_lab> >("E1_vs_E1"));

  // iterate over two different TCAs:
  using wrts_diff=Axis<1000, 0, 4000, STR("wrts diff cluster - main"),
                       [](auto& main, auto& cluster){ return int64_t(cluster.GetWRTS())-uint64_t(main.GetTimeStamp());},
                       R3BWRMasterData, R3BCalifaClusterData>; 
  hists.push_back(new AutoFillHist<int, AxisList<wrts_diff> >("wrts_diff"));
  // the following will automatically feed the same R3BCalifaClusterData to both axis:
  hists.push_back(new AutoFillHist<int, AxisList<wrts_diff, a_en_lab> >("wrts_diff_vs_E"));
  
  // iterate twice over the same data structure:
  using a_en_lab2=Axis<1000, 0, 10000,  STR("E_{Lab} in keV"), [](auto& a, auto& b){return b.GetEnergyDeposit();},
                       R3BCalifaClusterData, R3BCalifaClusterData>; // read "require two clusterData, return the seconds energy"
  // a_en_lab will (implicitly) give the energy of the first cluster, instead. 
  hists.push_back(new AutoFillHist<int, AxisList<a_en_lab, a_en_lab2> >("E1_vs_E2"));

  // filter out equal hits (ab)using the weight axis for a cut:
  using cut_different=Axis<1,0,1, STR(""), [](auto& a, auto& b){return &a != &b; }, R3BCalifaClusterData, R3BCalifaClusterData>;
  hists.push_back(new AutoFillHist<int, AxisList<a_en_lab, a_en_lab2, cut_different> >("E1_vs_E2_different"));

  //a histogram which does not depend on the actual entries of any TCA, but just their size:
  using a_cl_mul=Axis<100, 0, 100, STR("No of clusters"), [](){return Container<R3BCalifaClusterData>::get().size();}>;
  hists.push_back(new AutoFillHist<int, AxisList<a_cl_mul> >("cl_mul")); 

The caveats are:

  • C++ being the restrictive language that it is (kidding), passing a lambda as a template argument requires a state of enlightenment only available with GCCs -std=c++2a.
  • A ROOT is not currently compileable using that standard (and their cling is probably not up to date with LLVMs clang anyhow), this means that cling must not see any of the magic, so I put it in the cxx (and placed problematic headers out of its reach).
  • The price for that magic is some rather heavy functional-style template meta programming. This also means that given the slightest error, gcc will happily spew forth some 16 kB of call stacks.
  • There will be some minimal runtime overhead, as AutoFillHistBase::AutoFill is virtual (but then again, so is TH*::Fill), and we will have to iterate once per histogram over all the relevant TCAs, instead of putting all the Fill calls into the same loop.
  • If we do not need the Cartesian product, but just a small subset of it (e.g. all Cal-Hits whose ClusterID is the same as one of a given cluster), taking the product first and then filtering out allmost everything is obviously not efficient.
  • Arrays of histograms are not supported yet, but would be conceptionally easy to add. (Just have an additional lambda which returns a std::tuple specifying which histogram instance gets filled.)

Proposal: Generating ./geometry/*.root during build

From what I understand, the geometry root files are generated from macros/geo/create_${DETECTOR}.C.

Still, they are added to the repository. This could cause some possible problems:

  • Incremental changes become opaque. From gits point of view, a binary blob is just replaced by another binary blob.
  • There is always the exciting possibility that the generating macros and the binary root geometry file diverge, because someone added the binary change in the main repository but not the macro change in the macros repository, or vice versa.
  • Furthermore, at least the floating point operations used to generate the geometries are implementation dependent. So "let's run the create script and do a diff" is right out. One would have to do a semantic comparision.
  • Finally, this seems to encourage duplication. (See #317 .) At the moment, we have 14 geometries for califa, and 9 different create_califa_*.C scripts. Given that I had to re-add support for the 2019/s444 geometry, I would wager that most versions will fail to work with the current code base.

The largest file in geometries is some 150kBytes. I think it is both feasible and desirable to auto-generate the supported versions of these files (e.g. 2019, 2020) during the cmake build process.

What do you think?

Missing detectors in R3BMCTrack

To reproduce: run test file macros/r3b/run_sim.C() directly
Tested with 3b073bf (before the macros where removed from the main repository)

The detectors added in
90c9198#diff-7fe5d291e474bea07c4c9def6abcc1f7

are missing in R3BMCTrack::SetNPoints and R3BMCTrack::GetNPoints, which leads to many warning messages during simulation:

-E- R3BMCTrack::SetNPoints: Unknown detector ID 17
-E- R3BMCTrack::SetNPoints: Unknown detector ID 18
-E- R3BMCTrack::SetNPoints: Unknown detector ID 22
-E- R3BMCTrack::SetNPoints: Unknown detector ID 23
-E- R3BMCTrack::SetNPoints: Unknown detector ID 24
-E- R3BMCTrack::SetNPoints: Unknown detector ID 25

I would highly recommend ditching the current implementation of fNPoints, a overcomplicated Bitvector, in favor of, e.g., a std::array with size of the enum DetectorId.

Also, I don't know what this is part in R3BMCStack does, but is seems somewhat wasteful. Maybe just store the whole fPointsMap in R3BMCTrack?

      for (Int_t iDet=kREF; iDet<kLAST; iDet++) {
        pair<Int_t, Int_t> a(iPart, iDet);
        track->SetNPoints(iDet, fPointsMap[a]);
      }

Development in VSCode

Dear @hapol,

This is not an "issue" in itself but just a quick note that can save time for a lot of people that use IDE's like VSCode to develop R3BRoot and I think it could be added to the wiki as a simple note (I don't mind writing it), just need your authorization.

When writing the name of a class like "R3BCalifaCrystalCal2Hit" it would be pretty good to have an auto completion tool, and by just adding a simple .json file to the .vscode directory like this, allows for people to have the Fair and R3B Classes to be auto completed and that helps a lot while developing.


{
    "configurations": [
        {
            "name": "Linux",
            "includePath": [
                "${workspaceFolder}/**",
                "/home/teetos/Programs/FairRoot/**",
                "/home/teetos/Programs/FairSoft/**",
                "/home/teetos/Programs/R3BRoot/**"

            ],
            "defines": [],
            "compilerPath": "/usr/bin/gcc",
            "cStandard": "gnu17",
            "cppStandard": "gnu++14",
            "intelliSenseMode": "linux-gcc-x64",
            "configurationProvider": "ms-vscode.cmake-tools"
        }
    ],
    "version": 4
}

I know it is a minor detail but it think we can improve the wiki bit by bit :)

Kind regards,

Source of truth for start time

For NeuLAND calibration and online analysis, we currently rely on other detectors. The problem is that these detectors change from experiment to experiment and within the experiment the offset can change (e.g. on DAQ reboot).

For example, in the current version of the NeuLAND Online Analysis Script we do this with an ifdef switch, taking LOS by default and Sofia if it exists - not ideal. In addition, there is always some logic involved to extract the start time from the other detectors' data – something that does not belong in the NeuLAND code but in its own class
The offset is a parameter given in the online analysis script,

    auto nlhit = new R3BNeulandCal2Hit();
    nlhit->SetDistanceToTarget(distanceToTarget);
    nlhit->SetGlobalTimeOffset(7300);
    run->AddTask(nlhit);

Which obviously makes analyzing runs with different offsets together impossible.

Is there a common class, a “source of truth”, that I can simply query/consume for the start time? That should also take care of the changing part of the time offset as a run parameter (ParFile).
Depending on the experiment, one would add the respective task for the right start detector (which fill the same Container with the start time) to the macro.
How do the other detectors handle the start time?

Directory specific compiler flags

Compiler flags should be the same for all sub-folders and are to be defined on the level of top CMakeLists.txt. Please remove directory-specific definition in neuland/CMakeLists.txt.

Cheers,
Dima

Compile error on macos in R3BOnlineSpectraLosStandalone

Hi,

one of our last CI runs found an issue here:

/Users/alfaci/alfaci/workspace/FairRootGroup_FairSoft_PR-397/build/test_workdir/stage/spack-stage-r3broot-develop-myzse2azudm6cwj57nxbg2xc4qdbqo33/spack-src/r3bbase/R3BOnlineSpectraLosStandalone.cxx:453:18: error: variable-sized object may not be initialized
    Int_t nPartc[fNofLosDetectors] = { 0 };
                 ^~~~~~~~~~~~~~~~

Could you look into this?

Maybe consider something like this?

std::array<Int_t, fNofLosDetectors> nPartc{0};

Fiber online task

It seems to me, that the current online task for the fibers is the s494 one. Is that correct? Or did I just not find the s522 FiberOnline task?

Vote/Proposal: make dev the default branch

Our default branch is master, last updated in 2017. I propose we make dev the default branch instead.

Reasoning:
The default branch is what users see when they first browse the repository on github, or naively clone the repo. What they want in 99% of the cases is the latest trunk version, which is dev. At the moment, we are misleading causal observers to think that R3BRoot has not been under development since 2017, as well as confusing Newbie users (and distracted users who should know better, such as myself sometimes.)

FairRoot uses this dual branch system, but I would argue that their project is fundamentally convergent: while new features might still be added, there will be little reasons to do big changes in the existing code base. Also, they have the manpower to actually do regular releases: the last substantial changes to master seem to be some 3-4 month ago.
For R3BRoot, the situation is fundamentally different. For the foreseeable future, we will always have one more beam time with a new or changed detector. Always a moving target. "R3BRoot: the definite version" is not going to happen -- and that is okay.

Comparison to popular open source projects:
linux: https://github.com/torvalds/linux default=master seems to be the bleeding edge
gimp: https://gitlab.gnome.org/GNOME/gimp same
Apache: https://svn.apache.org/repos/asf/httpd uses svn internally, so their default branch is called trunk, otherwise same
ROOT: https://github.com/root-project/root same

In a nonbinding vote (e.g. Wikipedia Meinungsbild style), I hearby ask the contributors to state their preference for or against this proposal. :-)

(A more difficult issue to solve is the mixture of beamtime-dependent and experiment-independent code. I think that for analysing older beamtime data, many prefer an unofficial fork of the R3BRoot dev as it was shortly after the experiment. I think this is unfortunate, as this means that neither will upstream get any bug fixes they do, nor will they get any bugfixes from upstream. In the present system, most R3BRoot devs get paid for (or earn their degrees by) doing data analysis, not to write good code and commit it. They are typically willing to make a PR when their analysis is done, but have no great incentive to do so when it is complicated as in "figure out which local commits to my 2019 fork are not experiment-dependent but general useful and figure out how to cherry-pick them into the latest dev version for a PR". I predict this divergence will get greater in time.

One option would be to include plenty of tests for each beam time, e.g. saying "from this day forward, R3BRoot should support 2019-s444 forever". Another option would be to accept that divergences are going to happen and just create branches for every experiment with significant changes to any detectors.

Of course, all of this is just hearsay from my part, for all I know, the current version still handles S438b perfectly.)

Foo& operator=(const Foo&) { return *this; } considered harmful

git blame is not very forthcoming, but whoever has written this gem:

R3BCalifaCrystalCalData& operator=(const R3BCalifaCrystalCalData&) { return *this; }

has just cost me some two hours of debugging.

The only case where an assignment operator would be NOP is a class without member variables, which this class is evidently not.

If you have to trick the compiler (possibly because of ROOT) into thinking you provided a method which is not actually implemented, the least you could do would be to throw an exception if it was actually called.

\begin{soapbox}
I feel that in physics, data analysis code is often regarded as a tedious intermediate step between the data and the plots. As long as the plots look fine, who cares about how they were made?

Personally, I feel that this is wrong. Your code is as important a step in the chain of custody from the events to the plots as your detectors are. (So is your DAQ, btw). Buggy code might mess up good data in subtle ways to create wrong plots. And bad code is likely more prone to be buggy, as well.

(Of course, the incentives for most contributors (e.g. me) do not encourage high quality code. One writes code to create plots for a thesis (e.g. me) or publication. Afterwards, one might create a PR. If merging the PR involved a code review in which people were told to substantially rewrite their code, they probably would not bother. By contrast, in the software industry, programming (and reviewing, and post-review-fixing) is what people are actually paid to do. I have no idea how to fix this: insist on PR merge before thesis acceptance or publication approval? Have someone continuously fix code? Reject half of the PRs and risk fragmenting the project?)
\end{soapbox}

Addendum:

(0) deleted some unwarranted comparison to life-critical maintenance. (Sorry for that.)

(1) See http://cpp.sh/8n7qv for how this fails.

(2) I realize that this is endemic: the similar code appears in at least 28 other instances as well. (Further cases promise an assignment operator in the header and do not define it in cxx. Neuland instead deletes unwanted assignment operators. Good for them!) Nevertheless, it is wrong for any reasonable definition of wrong. Of course, this is C++, if one wanted to change the semantics of the assignment operator from "assigns variables" to "does nothing", "compares for equality" ("so users do not have to remember to use =="), or "calls delete on this", we are free to define that. C++ is not in the habit of protecting users from themselves.

Note that the standard library also relies on operator= obeying certain semantics, the bug which caused this rant was actually that std::sort would refuse to sort a std::vector.

Naturally, C++ is hard enough when one does follow good practices. When actively disregarding these by misusing operator overloads, templates, lambdas or any of the other potential footguns, one is no longer just staying in Gilman House, Innsmouth, but instead rowing out to the Reef at midnight chanting the names of Deep Ones.

Use several instances of the same detector in simulations

Hello, I am trying to use several instances of fibers (fi11) in a simulation, get several branches in the sim.root file, but only the first one is filled, ie Fi11Point_1 is filled but not Fi11Point_2. Is there another way to use the constructor to prevent such issue? below is my current version in the run_sim.C macro.
run->AddModule(new R3BFi11("doublebig_fi11.geo.root", {fi10pos.X(), fi10pos.Y(),fi10pos.Z()}, {"" ,9 0.0,90-angle,0.0}));

Thank you in advance. Cheers,
Anna

Against (some uses of) TClonesArray

When reading R3BRoot code, one common occurrence is the use of a TClonesArray where another data structure would be more appropriate. (I am not talking about std::vector here, which is technically always superior to a TCA unless the actual type of your members is really TObject.)

Mapped hits, no matter from which detector, (almost?) always come with a unique channel id.

The appropriate data structure for such data is an associative array, typically either implemented as a search tree or a hash map. std::map in C++, dict in python etc.

There are two kinds of styles to deal with the lack of lookup. The first one is to just loop over the TCA and search for the crystalId (or whatever). The other is to create a local std::map<uintFoo_t, R3BBar*> in Exec(), fill it in O(n*log(n)), retrieve in O(log(n)).

Both are bad because they add code which would not be needed if we had used the correct data structure in the first place.

While FairRootManager allows the storage of arbitrary objects (probably through void*?), anything stored there will probably not be serializable to root files.

Further alternatives are:

  • Using TMap: extremely ugly, I can see using the overhead of a TObject for the mapped type, but for the key type it seems excessive.
  • Using a not zero-compressed array: Slow as hell if most channels are zero most of the time
  • Using a separate array of offsets: Ugly, uncomfortable to use.

A usable workaround might be to use the existing TCA wrappers (e.g. @janmayer's TCA*Connector or my (upcoming) roothacks::Container) and add a map-mode/pedant to them.
A r3bdata class could then define a uint64_t key() method which returned an appropriate key (such as the crystal id).

Using a global map of TCA* to std::map-like structures, (plus keeping track of the eventnos of the last updates) one could avoid mapping the same data repeatedly. (Might not be worth it, though.)

This would bypass the serialization issue altogether, but impose a small overhead when reading from a file.

My main motivation here is not so much runtime improvements but code size improvements.
Instead of an explicit for loop and compare (as seen e.g. here), one could simply use (with a suitable default initializer and operator+=): cal[crystalId]+=(mypoint).

Naturally, Jans comment that from issue #436 also applies here: this is really something which should be provided by FairRoot, as I imagine that different experiments also happen to use detectors featuring channel numbers. Just exposing whatever ROOT implemented a quarter-century ago is not good enough.

testR3BPhaseSpaceGenerator.cxx appears to be broken.

Hi (again),

There's an explicit virtual method override that won't override --and because the keyword override is used, that generates a compiler issue. Indeed, it's a function overload, not a reimplementation.

/usr/local/FAIR/R3BRoot/r3bgen/testR3BPhaseSpaceGenerator.cxx:17:14: error: ‘void {anonymous}::MockFairPrimaryGenerator::AddTrack(Int_t, Double_t, Double_t, Double_t, Double_t, Double_t, Double_t, Int_t, Bool_t, Double_t, Double_t, Double_t)’ marked ‘override’, but does not override
void AddTrack(Int_t pdgid,
^~~~~~~~

The function takes a different list of parameters from how the virtual method is declared, thus making it an overload instead.

FairPrimaryGenerator.h:83
virtual void FairPrimaryGenerator::AddTrack(Int_t pdgid, Double_t px, Double_t py, Double_t pz,
Double_t vx, Double_t vy, Double_t vz,
Int_t parent = -1, Bool_t wanttracking = true,
Double_t e = -9e9, Double_t tof = 0.,
Double_t weight = 0., TMCProcess proc = kPPrimary);

whereas:

testR3BPhaseSpaceGenerator.cxx:17
void testR3BPhaseSpaceGenerator::AddTrack(Int_t pdgid,
Double_t px,
Double_t py,
Double_t pz,
Double_t vx,
Double_t vy,
Double_t vz,
Int_t parent = -1,
Bool_t wanttracking = true,
Double_t e = -9e9,
Double_t tof = 0.,
Double_t weight = 0.) override

The problem is, the last TMCProcess is missing. Adding it will solve the problem.

I'm using the very last commit in FairRoot/dev.

Some historical background: [email protected] apparently added the new argument to FairPrimaryGenerator::AddTrack with commit 45de553b9da50e89a386f5fd3b40c8289ebf1de2 on the 28th of June this year. Who compile-tested the last commits of R3BRoot appears to have an old FairRoot version (and should update).


EDIT: a chat with Vadim clarified why it actually passed the compile-test: I'm using a FairRoot version that is too up to date. Anyhow, this is the solution to a future problem.

Califa clusterization not working well

After some analysis of the s455 data we realized that the clusterization procedure for Califa is not optimal. A variable
Double_t fThreshold; // Minimum energy requested in a crystal to be included in a Cal
is defined in the task, but this is not complete : this sets the minimum energy of a crystal to be included in a cluster, but not the minimum energy that defines a cluster.
So with this you have two options in a typical califa event : set this variable to a low value and make dozens or hundreds of clusters including background (and wait for some weeks for the code to finish) or set this value to a higher energy (above 2,3,4 MeV) and lose all the energy around a crystal with a typical proton hit . This was the cause that for the proton beam in 2020 we always obtained a kinematic line in Califa under the theoretical one (atached picture).
The correct way of doing this would be to define two variables : one for the minimum energy in a crystal to be considered as a possible cluster and another one to set the minimum energy of a crystal to be included in a cluster. I could do this by myself, but not sure if this is an auto& = std::whatever ::static<dynamic_cast ....> or just a boolean ... what do you think @klenze?

califa_matrix
Captura de pantalla de 2022-04-18 11-41-04

Califa simulations

Hello! I'm working in simulations with Califa and got an error while doing them.

Important information

  • Ubuntu 20.04
  • Using R3BRoot on dev branch and macros in dev branch as well.

Problem

When I run simulations in macros/r3b/califa/simulations/ I can run the runsim.C script with no problems, then when I want to see the events and run califaeventdisplay.C, go to Fair Event Manager and change the "Current Event" I get the following error:

*** Break *** segmentation violation



===========================================================
There was a crash.
This is the entire stack trace of all threads:
===========================================================
#0  0x00007efd5682cc6a in __GI___wait4 (pid=9080, stat_loc=stat_loc
entry=0x7fff09f343a8, options=options
entry=0, usage=usage
entry=0x0) at ../sysdeps/unix/sysv/linux/wait4.c:27
#1  0x00007efd5682cc2b in __GI___waitpid (pid=<optimized out>, stat_loc=stat_loc
entry=0x7fff09f343a8, options=options
entry=0) at waitpid.c:38
#2  0x00007efd5679bf97 in do_system (line=<optimized out>) at ../sysdeps/posix/system.c:172
#3  0x00007efd56ed284e in TUnixSystem::StackTrace() () from /home/teetos/Programs/FairSoft/build/lib/root/libCore.so.6.16
#4  0x00007efd56ecf52c in TUnixSystem::DispatchSignals(ESignals) () from /home/teetos/Programs/FairSoft/build/lib/root/libCore.so.6.16
#5  <signal handler called>
#6  0x00007efd56e3df2b in TObjArray::GetAbsLast() const () from /home/teetos/Programs/FairSoft/build/lib/root/libCore.so.6.16
#7  0x00007efd52dbb9c4 in TObjArray::GetEntriesFast (this=<optimized out>) at /home/teetos/Programs/FairSoft/build/include/root6/TObjArray.h:65
#8  R3BCalifaEventDisplay::Exec (this=0x55ebf869e5a0, opt=<optimized out>) at /home/teetos/Programs/R3BRoot/R3BRoot/evtvis/R3BCalifaEventDisplay.cxx:163
#9  0x00007efd4b7b7306 in FairTask::ExecuteTasks (this=0x55ebfc035500, option=0x7efd4b7ec6a5 "") at /home/teetos/Programs/FairRoot/FairRoot/base/steer/FairTask.cxx:186
#10 0x00007efd4b7b6f1a in FairTask::ExecuteTask (this=0x55ebfc035500, option=0x7efd4b7ec6a5 "") at /home/teetos/Programs/FairRoot/FairRoot/base/steer/FairTask.cxx:149
#11 0x00007efd4b7a9806 in FairRunAna::Run (this=0x55ebfbbea5d0, entry=<optimized out>) at /home/teetos/Programs/FairRoot/FairRoot/base/steer/FairRunAna.cxx:513
#12 0x00007efd4a02cf52 in FairEventManagerEditor::SelectEvent (this=0x55ec0126c290) at /home/teetos/Programs/FairSoft/build/include/root6/TGNumberEntry.h:211
#13 0x00007efd40d7c02a in ?? ()
#14 0x0000000000000000 in ?? ()
===========================================================


The lines below might hint at the cause of the crash.
You may get help by asking at the ROOT forum http://root.cern.ch/forum
Only if you are really convinced it is a bug in ROOT then please submit a
report at http://root.cern.ch/bugs Please post the ENTIRE stack trace
from above as an attachment in addition to anything else
that might help us fixing this issue.
===========================================================
#6  0x00007efd56e3df2b in TObjArray::GetAbsLast() const () from /home/teetos/Programs/FairSoft/build/lib/root/libCore.so.6.16
#7  0x00007efd52dbb9c4 in TObjArray::GetEntriesFast (this=<optimized out>) at /home/teetos/Programs/FairSoft/build/include/root6/TObjArray.h:65
#8  R3BCalifaEventDisplay::Exec (this=0x55ebf869e5a0, opt=<optimized out>) at /home/teetos/Programs/R3BRoot/R3BRoot/evtvis/R3BCalifaEventDisplay.cxx:163
#9  0x00007efd4b7b7306 in FairTask::ExecuteTasks (this=0x55ebfc035500, option=0x7efd4b7ec6a5 "") at /home/teetos/Programs/FairRoot/FairRoot/base/steer/FairTask.cxx:186
#10 0x00007efd4b7b6f1a in FairTask::ExecuteTask (this=0x55ebfc035500, option=0x7efd4b7ec6a5 "") at /home/teetos/Programs/FairRoot/FairRoot/base/steer/FairTask.cxx:149
#11 0x00007efd4b7a9806 in FairRunAna::Run (this=0x55ebfbbea5d0, entry=<optimized out>) at /home/teetos/Programs/FairRoot/FairRoot/base/steer/FairRunAna.cxx:513
#12 0x00007efd4a02cf52 in FairEventManagerEditor::SelectEvent (this=0x55ec0126c290) at /home/teetos/Programs/FairSoft/build/include/root6/TGNumberEntry.h:211
#13 0x00007efd40d7c02a in ?? ()
#14 0x0000000000000000 in ?? ()
===========================================================

This does no happen when I run the exact same geometry and run a simulation in /macros/r3b/ and use run_sim.C and eventdisplay.C. The problem when running in the general simulation folder and not the CALIFA one is that I only have access to Point Data and I want Hit.

I've tried with different geometries but can't get it to work.

Kind regards

Event Header Ambiguity

Hans and I got a root file after Cal2HIt with two event headers. We looked into the R3BRoot code and found that the lifetime and owner of the R3BEventHeader is not well defined, it even leaks into the macros. Could someone please have a look?

Masses in R3BRoot / FairRoot

I stumbled over a bug with masses in R3BRoot/FairRoot: The MCTrack branch filled during Simulation does not contain the masses for ions anymore, i.e.:

tfile = ROOT.TFile.Open(simfile)
ttree = tfile.Get("evt")
for event in ttree:
    print(event.MCTrack.GetEntries())
    for mct in event.MCTrack:
        print("\t", mct.GetPdgCode(), mct.GetMotherId(), mct.GetMass())
7
	 1000501310 -1 0.0
	 2112 -1 0.939565
	 1000020040 1 0.0
	 1000020040 1 0.0
	 1000020040 1 0.0
	 2112 1 0.939565
	 2212 1 0.938272

I briefly looked when and why that changed, but couldn't find it. I found some strange logic in FairRoot and some legacy in R3BMCTrack, but oh well.

For the primary particles I could fix that, e.g. in the Ascii Generator, by explicitly passing the mass to AddTrack but then I
a) have to re-simulate everything again
b) rely on the values in the input files (which should not contain this information, especially not repeated 10000 times)
c) still have no masses for secondary ions (currently not a big problem)
d) have the wrong masses from the TDatabasePdg, i.e. 0.939 565 00 vs 0.939 565 361 in the Input-file vs the actual value 0.939 565 420 52(54) vs whatever is actually used in the simulation.

Isn't there some database included one can query easily? In principle, that is just using the existing list of data for all nuclei (and particles) ...

Fibers: Hit-Level calibration

Regarding Fiber (30-33) calibrations:

For Cal-Level: We have the Mapped2Cal class as well as the Mapped2CalPar class to generate parameters.
For Hit-Level: We have Cal2Hit class to read parameters, but I can't seem to find the class to generate Hit-level parameters. Are these classes/functions hidden somewhere else, or are they non existent at all?

Preview: Lightweight FairTasks PoC

Writing a typical FairTask traditionally means creating lots of boilerplate code:

  • Adding an TClonesArray* member field for every R3BFooData one wants to use
  • Add a constructor which uses member initialization lists to set these to nullptr (I see few default member initializers)
  • Adding an Init() method in which the TCAs are assigned from FairRootManager::Instance()->GetObject("FooName"), typically using a C-style cast, plus some error handling
  • Adding an Exec() method where the (assumed) TCAs are queried for their wlements, and these elements are C-style cast to whatever the programmer assumes them to be
  • Adding a Destructor which deletes all the TCA pointers on the probably erroneous assumption that FairRootManager::GetObject transfers ownership (but then again no harm was ever done by a double free or use after free)

For Parameters, the situation is quite similar, but seems to involve two more methods, SetParContainers() and SetParameter().

Eternal optimist that I am, I think the reason why our FairTasks get so long is that given these Boilerplate requirements, it is much easier to add the stuff into an existing Task than writing a new one.

Using some template magic (and some features of C++17), one can make this procedure both much safer (e.g. using dynamic_casts) and hide the complexity from the individual FairTasks.
Here is a sample FairTask meant to write out WRTS of s494 events where the ToFD saw a carbon-ish ion. (The cxx is just two lines, the include and the ClassImp macro.)

The boilerplate per R3BFooData practically goes down to #include "R3BFooData.h. To use it, one can then simply use
for(auto& h: roothacks::Container<R3BFooData>::get())

(If the TCA-name is not unique per type (unlikely, given that we have four otherwise identical R3BWRFooData), one would have to specify the TCA object name as well. Of course, the mapping ClassName->ObjectName must be maintained somewhere, one line per FooData.)

I will probably make a PR with the supporting code (plus a short sample task) when my analysis is done.

Build of neuland directory fails on macOS 11.1

FairSoft: jun19p2
FairRoot: v18.2.1

Error message:

[kresan@Dmytro-Kresans-iMac neuland ]$ make
[  3%] Built target R3BTraRene
[ 53%] Built target R3BData
[ 60%] Built target R3Bbase
[ 60%] Generating G__R3BNeulandSharedDict.cxx, G__R3BNeulandSharedDict_rdict.pcm, ../../lib/libR3BNeulandShared.rootmap
input_line_12:818:22: error: constexpr function never produces a constant expression [-Winvalid-constexpr]
    constexpr double NaN2Value(const double val, const double valIfNaN = 0.)
                     ^
input_line_12:820:17: note: non-constexpr function 'isfinite<double>' cannot be used in a constant expression
        return (std::isfinite(val) ? val : valIfNaN);
                ^
/Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/bin/../include/c++/v1/math.h:441:1: note: declared here
isfinite(_A1 __lcpp_x) _NOEXCEPT
^
Error: /cvmfs/fairsoft.gsi.de/macos-10.15/opt/darwin-catalina-x86_64/clang-11.0.0-apple/root-6.16.00-udx4vrh3rawbmvqno5675dvkattllxbw/bin/rootcint: compilation failure (/Users/kresan/SSD2/R3BRoot/github/builds/dev-b/neuland/shared/G__R3BNeulandSharedDict12c1b60120_dictUmbrella.h)
make[2]: *** [neuland/shared/G__R3BNeulandSharedDict.cxx] Error 1
make[1]: *** [neuland/shared/CMakeFiles/R3BNeulandShared.dir/all] Error 2
make: *** [all] Error 2
[kresan@Dmytro-Kresans-iMac neuland ]$

@janmayer can you have a look, please?

CMake Failed

Hi, after I installed FairSoft and FairRoot successfully, I had a problem with the CMake step in R3BRoot which gives the error below :
(PC system : Ubuntu 20.04; gcc 9.3.0; cmake 3.16.3; FairSoft apr21; FairRoot v18.2.0-349-gfae563fdf;
R3BRoot may21-4-g82ade09b)

#-- Could not find FairCMakeModules. It is recommended to install https://github.com/FairRootGroup/FairCMakeModules
-- Setting FairRoot environment:
-- FairRoot prefix : /home/s034/fair_install/FairRootInst
-- FairRoot Library directory : /home/s034/fair_install/FairRootInst/lib
-- FairRoot Include path : /home/s034/fair_install/FairRootInst/include
-- FairRoot Cmake Modules : /home/s034/fair_install/FairRootInst/share/fairbase/cmake
CMake Error at CMakeLists.txt:104 (find_package2):
Unknown CMake command "find_package2".

-- Configuring incomplete, errors occurred!

By the way, my installation method is:
mkdir ~/R3BRoot_install
cd ~/R3BRoot_install
git clone https://github.com/R3BRootGroup/R3BRoot.git
cd R3BRoot
git checkout dev
git clone https://github.com/R3BRootGroup/macros.git
mkdir ../build
cd ../build
export SIMPATH=~/fair_install/FairSoft_src/install
export FAIRROOTPATH=~/fair_install/FairRootInst
cmake ../R3BRoot/

Can anybody help me? Thank you so much in advance.
CMakeOutput.log
CMakeLists.txt

Proposal: make data containers structs (inheriting from TObject)

From my understanding of good C++, classes are appropriate when there are invariants.

This is generally not the case for the stuff residing in r3bdata.

Furthermore, this leads to constructor calls with many parameters, as in:
new ... R3BCalifaPoint(trackID, detID, ident, posIn, momIn, time, length, eLoss, Nf, Ns, EventId);

Unlike Python, C++ does not allow named parameters (But the authors of the eight-parameter TH2D constructors are proposing to add them). For now, order matters, and no reader will ever know if eLoss comes before or behind Ns and Ns.

While aggregate instantiation (3-4) could eventually be used with structs (which would have to be TObject wrapped by some template magic), I do not think we will adopt C++20 before FAIR starts. :-(

For now, I would propose:

  • making member variables public if there are no invariants
  • default-setting them: uint32_t foo{};
  • instantiating the struct with default values, then setting the members.

struct R3BFoo: public TObject
{
uint32_t bar{};
uint64_t baz{};
// ...
ClassDef...
};
// when constructing
auto obj=new R3BFoo();
obj.bar=myBar;
obj.baz=myBaz;

This way, the causal reader can check that the the bar and baz fields are indeed not switched.

Problems with some initializations

Please, don't use this kind of initialization:

Int_t nsum_top[fNofPlanes] = { 0 };

error: variable-sized object ‘nsum_top’ may not be initialized
Int_t nsum_top[fNofPlanes] = { 0 };

Thanks in advance

R3BMCTrack crash in Macros

Hi,

After the new changes to the R3BMCTrack class and using the proper function calling (GetFourMomentum instead of GetMomentum... etc) I have experienced some crashes in the code when using this object from standard macros as checkResults:

Event:0
root.exe(10516,0x116da95c0) malloc: Incorrect checksum for freed object 0x7fda5b9eeeb8: probably modified after being freed.
Corrupt value: 0x0
root.exe(10516,0x116da95c0) malloc: *** set a breakpoint in malloc_error_break to debug_

Could anyone take a look to this bug?

Thanks!

Geometry file for CALIFA missing

CI test for CALIFA is failing with error message:
[FATAL] R3BCalifa: geometry file califa_2020_s444.geo.root not found in standard path

@gabrigarjim, could you please add it to this repository, or make a fix in R3BRootGroup/macros?

Missing file r3bdata/fibData/R3BFi4CalItem.cxx ?

Hi,
After a linker fail with R3BFi4CalItem::R3BFi4CalItem(unsigned char, unsigned int, unsigned int, unsigned int, float, float, float, float), I noticed that there's an orphan header file:
/r3bdata/fibData/R3BFi4CalItem.h
It was added in commit d83d357:

$ git rev-list -n 1 HEAD -- $( find . -name '3BFi4CalItem.*' ) #the find command will only find the header

doing the same thing for the .cxx doesn't get any result --the file has never been in the repo or was removed before the history began.

Could you please add the file back/remove the header if it's not needed?

Note that the missing .cxx file doesn't affect the build, nor the creation of shared libraries, but only linking against the library in question, libR3BFi4.so.

I can avoid linking against it ATM, but if someone needs the affected class R3BRoot is going to explode in their face...

thoughts on parameter formats

I think the way parameter files (e.g. calibration) are handled in FairRoot/R3BRoot is terrible.

Custom classes inheriting from TObject are painful enough when you are dealing with TClonesArrays (where one could argue that the benefits in speed and size justify the pains of ROOT), but for the parameter files they are a terrible design choice. A calibration just for califa (payload perhaps 40kB worth of ascii encoded float) goes for 250kB in the par format (all serialized arrays with at least 2432 elements, most of it stuff like APD numbers) or more than 1MB (with ROOT, most of it histograms).

Naturally, FairRoot does no collision checking when the same object in multiple *par files (it seems the earlier one in the TList will win), and at least in R3BRoot, we also do not even check for the existence of input parameters: R3BCalifaMap2CrystalCal will happily read a (default-constructed?) zero array from FairRuntimeDB if the no files were specified. This of course violates "Fail as early as possible".

I want to propose a solution offering the following features:

  • Multi-Format support, including (potentially) human readable ones used by people which have not been exposed to ROOT (such as csv, json, xml)
  • Good support for mixing and replacing individual parameter sets (e.g. "Take the califa cal from s444 with the TofD cal from s494")
  • Enforcement of parameter existence
  • Enforcement of unique definitions
  • Namespace support
  • Possibility of version control

I'm am talking, of course, of this new and shiny feature called "directory" (or "folder" for Apple users) in the recent innovation called "hierarchical file system". Furthermore, I propose a single environment variable $R3BPARS, which will point to a parameter directory.

So R3BCalifaMap2CrystalCal might just look for $R3BPARS/califa/calibration.json (or .csv, or .xml) and parse that, easy-peasy. If it turns out that 3d models stored in root files are really the way to go (instead of procedurally generating everything at startup a la geant), we could easily accommodate them as well. Backwards compatibility is easily achieved: feed $R3BPARS/par/.par and $R3BPARS/root/.root to R3BRuntimeDB.

By having a dedicated class (call it R3BParManager) or something managing parameter file lookup (e.g. pasting env var + subpath), we could later also support e.g. validity time intervals for parameter files to transparently support multiple beamtimes. (e.g. take the first wrts, and search in the subdirectories which are valid for that time for the subpath. If you find exactly one match, return that, otherwise, error. In the end, this will just return a filename: R3BParManager::get("califa/calibration.json") for epoch 1591741032 resolves to $R3BPARS/202105_s494/califa/calibration.json.)

Thus, this will be much more legible than the present approach. For comparison, here is the relevant output of FairRuntimeDB::print if I used a TList for both the first and the second input (after initialization, just before starting the run)

--------------  actual containers in runtime database  -------------------------
FairBaseParSet                                 class for parameter io
FairGeoParSet                                  class for Geo parameter
califaCrystalCalPar                            Califa Calibration Parameters
CalifaTotCalPar                                Califa Tot Cal parameters
--------------  runs, versions  ------------------------------------------------
run id
  container                                        1st-inp    2nd-inp    output
run: 5
  FairBaseParSet                                        -1         -1          0
  FairGeoParSet                                         -1         -1          0
  califaCrystalCalPar                                   -1         -1          0
  CalifaTotCalPar                                       -1         -1          0
--------------  input/output  --------------------------------------------------
first Input:
Ascii I/O /what/ever/all_101442.par is open
detector I/Os:  FairGenericParIo
second Input:
OBJ: FairParRootFile    allParams_20211118_205834.root   : 0 at: 0x5637eaceadf0
Root file I/O allParams_20211118_205834.root is open
detector I/Os:  FairGenericParIo
output: none

The only relevant information (apart from the fact that your directories get spammed with all* files) here is that both TLists somewhere included some FairGenericParIo, and the names of the different parameters used. (Or the names of their classes, rather hard to tell).
Not visible:

  • What input files were used
  • Which input files define which parameter names (of which classes)
  • If there were collisions, which files definition won? (This -1 would indicate "not present", I guess, but actually califaCrystalCalPar was taken from one of the input files.)

One perceived downside of this proposal is that different people have different formats they like and want to use. So different detectors will pick different formats, dragging in software requirements for parsing xml, json, bmp, sqlite, ods and so forth. I think this argument would be more valid if the current standard was less painful. e.g. if I were an xml fanboi and wanted to write my parameter file in xml when all other detectors used json, or vice versa. Still, I think that making nlohmann/json or zeux/pugixml a subrepository of R3BRoot is probably painful enough that it is unlikely that many people will go through the troubles of adding another option for parsing structured text if there is already one available. Besides, $SIMPATH is already 7.2GiB.

In my experience, stuff from ROOT gets used by FairRoot regardless of alternatives (like FairParFooFile::open taking a TList of TObjString instead of a STL vector or std::string), and anything from FairRoot gets used by R3BRoot the same way. I can only speak for myself, but I am confident that neither the ROOT devs nor the FairRoot devs have much in the way of kompromat on me. We as devs have the ability to pick stuff we like from FairRoot/ROOT and replace stuff we don't like from the wider free software world outside HEP.

So if I get around to fixing the califa calibration format, I will simply skip FairRuntimeDB for something which feels less painful.

PS: the automatic histogram creation based on axis definitions is working nicely, I will probably make a PR after I finish writing my PhD and just make cmake compile all of that conditionally on GCC_VERSION>=10 (or equivalent clang).

[rant] Code duplication

For a fun exercise, run
find . -iname \*.cxx | xargs cat | grep -v include | gcc -E - | sed 's/^[ \t]*//' | sort | uniq -cd | sort -h | less

Pick a nontrivial line with a high duplication count, such as

gGeoManager->SetCurrentDirection(newdirection);

(which appears 36 times in the code), then run an appropriate grep pipe like in

grep -C 10 -F "gGeoManager->SetCurrentDirection(newdirection);" -r * | less

Notice how virtually the same block of code appears 36 times in our project. (kudos to xball/R3BXBall.cxx, for being the only ones to remove the //TGeoNode *bla comment line.)

I am not a software designer, but from my perspective, this does not seem like code which can be maintained easily. If you copy a file, chances are that both versions will slowly diverge, resulting in twice as much legacy code.

For a perhaps more recent example, take the fibers. At the moment, we have 17 directories matching "fi[0-9]+[ab]?". At the top level, no less. Each contains a different Mapped2Cal.h class. In my opinion, this raises the question: "what is unique about the calibration process of fiber detector 7?" I am not a fiber person, so I don't know. If fi7 channels are calibrated using a pol2, while all the other fibers use pol1, then that might be a good reason to have separate calibration code for fi7. If it is just "it uses different collection names from fi6", that is not a good reason, IMHO.

OOP (and C++ in particular with TMP) offers powerful tools for abstraction.
If handling all the fiber detectors in one task/collection is not an option, why not use

template <int N, char suffix='\0' >
class R3BFiber
{ ...
};

That way, one still has the power to specialize when needed (if fi7 needs a pol2 calibration or whatever) without creating 17x as much legacy code.

Backup copies in the repository are another pet peeve of mine. Take califa/unpack/oldCode. We have git. At the most, a comment in the new version "rewrite, see bf5282e for old version" should be enough.

TL;DR: commit code like you had to pay per line added.

Just my 2 cents. Sorry for the rant and apologies to the detectors I singled out.

Shift count overflow: R3BCalifaFebexReader

At line 63 in r3bsource/R3BCalifaFebexReader.cxx:
bitwise shift count of 32 is equal to size of uint32_t:

uint64_t timestamp = ((uint32_t) fData->CALIFA_TSMSBv[crystal] << 32)
      | (uint32_t) fData->CALIFA_TSLSBv[crystal];

Should we use uint64_t in the casts?

Cheers,
Dima

Compilation error with gcc-5.1.1, FairRoot(v-15.07a), FairSoft(jul15p1)

Hello,

Within this configuration, master or dev of R3BRoot (jul15) doesn't compile ... does it support ROOT 5 ?!

[ 39%] Built target R3BGfi
[ 39%] Built target libR3BGfi.rootmap
[ 41%] Built target R3BLandDB
[ 41%] Building CXX object land/CMakeFiles/R3BLand.dir/G__R3BLandDict.cxx.o
In file included from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.h:46:0, fromPATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:17:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h: In function ‘ROOT::TGenericClassInfo* ROOTDict::GenerateInitInstanceLocal(const std::vector<R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit>)’:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h:58:9: error: ‘struct R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit’ is protected
struct R3BLandDigitizer_CFD_Paddle_Hit
^
PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:4435:68: error: within this context
static ROOT::TGenericClassInfo *GenerateInitInstanceLocal(const vector<R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit>
)
^
In file included from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.h:46:0,
from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:17:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h:58:9: error: ‘struct R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit’ is protected
struct R3BLandDigitizer_CFD_Paddle_Hit
^
PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:4437:7: error: within this context
vector<R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit> ptr = 0;
^
In file included fromPATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.h:46:0,
from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:17:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h:58:9: error: ‘struct R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit’ is protected
struct R3BLandDigitizer_CFD_Paddle_Hit
PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:4438:69: error: within this context
static ::TVirtualIsAProxy
isa_proxy = new ::TIsAProxy(typeid(vector<R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit>),0);
^
In file included from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.h:46:0,
from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:17:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h:58:9: error: ‘struct R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit’ is protected
struct R3BLandDigitizer_CFD_Paddle_Hit
^
PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:4441:26: error: within this context
typeid(vector<R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit>), ::ROOT::DefineBehavior(ptr, ptr),
^
In file included from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.h:46:0,
from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:17:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h:58:9: error: ‘struct R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit’ is protected
struct R3BLandDigitizer_CFD_Paddle_Hit
^
PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:4443:26: error: within this context
sizeof(vector<R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit>) );
^
In file included from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.h:46:0,
from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:17:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h:58:9: error: ‘struct R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit’ is protected
struct R3BLandDigitizer_CFD_Paddle_Hit
^
PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:4449:112: error: within this context
instance.AdoptCollectionProxyInfo( ::ROOT::TCollectionProxyInfo::Generate( ::ROOT::TCollectionProxyInfo::Pushback< vector<R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit> >()));
^
In file included from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.h:46:0,
from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:17:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h: At global scope:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h:58:9: error: ‘struct R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit’ is protected
struct R3BLandDigitizer_CFD_Paddle_Hit

PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:4453:91: error: within this context
static ::ROOT::TGenericClassInfo _R__UNIQUE(Init) = GenerateInitInstanceLocal((const vector<R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit>)0x0); R__UseDummy(R__UNIQUE(Init));
^
In file included from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.h:46:0,
from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:17:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h: In function ‘void ROOTDict::vectorlER3BLandDigitizer_CFDcLcLR3BLandDigitizer_CFD_Paddle_HitgR_Dictionary()’:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h:58:9: error: ‘struct R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit’ is protected
struct R3BLandDigitizer_CFD_Paddle_Hit
^
PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:4457:52: error: within this context
::ROOTDict::GenerateInitInstanceLocal((const vector<R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit>
)0x0)->GetClass();
^
In file included from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.h:46:0,
from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:17:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h: In function ‘void_ ROOTDict::new_vectorlER3BLandDigitizer_CFDcLcLR3BLandDigitizer_CFD_Paddle_HitgR(void_)’:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h:58:9: error: ‘struct R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit’ is protected
struct R3BLandDigitizer_CFD_Paddle_Hit
^
PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:4465:57: error: within this context
return p ? ::new((::ROOT::TOperatorNewHelper_)p) vector<R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit> : new vector<R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit>;
^
In file included from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.h:46:0,
from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:17:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h:58:9: error: ‘struct R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit’ is protected
struct R3BLandDigitizer_CFD_Paddle_Hit
^
PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:4465:125: error: within this context
return p ? ::new((::ROOT::TOperatorNewHelper_)p) vector<R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit> : new vector<R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit>;
^
In file included from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.h:46:0,
from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:17:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h: In function ‘void_ ROOTDict::newArray_vectorlER3BLandDigitizer_CFDcLcLR3BLandDigitizer_CFD_Paddle_HitgR(Long_t, void_)’:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h:58:9: error: ‘struct R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit’ is protected
struct R3BLandDigitizer_CFD_Paddle_Hit
^
PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:4468:56: error: within this context
return p ? ::new((::ROOT::TOperatorNewHelper_)p) vector<R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit>[nElements] : new vector<R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit>[nElements];
^
In file included from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.h:46:0,
from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:17:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h:58:9: error: ‘struct R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit’ is protected
struct R3BLandDigitizer_CFD_Paddle_Hit
^
PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:4468:135: error: within this context
return p ? ::new((::ROOT::TOperatorNewHelper_)p) vector<R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit>[nElements] : new vector<R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit>[nElements];
^
In file included from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.h:46:0,
from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:17:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h: In function ‘void ROOTDict::delete_vectorlER3BLandDigitizer_CFDcLcLR3BLandDigitizer_CFD_Paddle_HitgR(void_)’:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h:58:9: error: ‘struct R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit’ is protected
struct R3BLandDigitizer_CFD_Paddle_Hit
^
PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:4472:16: error: within this context
delete ((vector<R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit>)p);
^
In file included from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.h:46:0,
from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:17:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h: In function ‘void ROOTDict::deleteArray_vectorlER3BLandDigitizer_CFDcLcLR3BLandDigitizer_CFD_Paddle_HitgR(void
)’:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h:58:9: error: ‘struct R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit’ is protected
struct R3BLandDigitizer_CFD_Paddle_Hit
^
PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:4475:19: error: within this context
delete ;
^
In file included from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.h:46:0,
from PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:17:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h: In function ‘void ROOTDict::destruct_vectorlER3BLandDigitizer_CFDcLcLR3BLandDigitizer_CFD_Paddle_HitgR(void_)’:
PATH_TO_WORK/GSI/R3BRoot/source/land/R3BLandDigitizer_CFD.h:58:9: error: ‘struct R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit’ is protected
struct R3BLandDigitizer_CFD_Paddle_Hit
^
PATH_TO_WORK/GSI/R3BRoot/build/land/G__R3BLandDict.cxx:4478:15: error: within this context
typedef vector<R3BLandDigitizer_CFD::R3BLandDigitizer_CFD_Paddle_Hit> current_t;
^
land/CMakeFiles/R3BLand.dir/build.make:827: recipe for target 'land/CMakeFiles/R3BLand.dir/G__R3BLandDict.cxx.o' failed
make[2]: *_* [land/CMakeFiles/R3BLand.dir/G__R3BLandDict.cxx.o] Error 1
CMakeFiles/Makefile2:1521: recipe for target 'land/CMakeFiles/R3BLand.dir/all' failed
make[1]: *** [land/CMakeFiles/R3BLand.dir/all] Error 2
Makefile:126: recipe for target 'all' failed
make: *** [all] Error 2

My recommendations for the further development of R3BRoot

Hi all. During the last years, I have become very familiar with R3BRoot. These are my recommendations for improving the code base that I didn't find the time to fix myself. Some are unnegotiable must-dos others are just nice to have (and everything in between).

Remove the connection to the macro directory

At some point, the macro directory was separated out due to frequent changes. However, it contains tests and is required in the building process. I would argue that this disruption to the automated testing, the commit system, and especially the user experience are no longer justified. There also seem to be several macros no longer used or maintained. Thus, I propose:

  • Move the tests to the respective detector directories
  • Move geometry creating macros to geometry/macros
  • Delete old code
  • Remove the macro directory dependence in the main CMakeLists.txt
  • Move (few!) files that are still useful to the main repository

Host UCESB and UPEXPS on GitHub

There is something mystical about UCESB & Co. Few people know how to work with it, and even fewer know how it works. Yet, they are essential components of R3BRoot.

I see it as an absolute necessity to host these two packages on GitHub. The current maintainers should, of course, have administrative access.

  • Create and push to R3BRootGroup/UCESB
  • Create and push to R3BRootGroup/UCEXPS
  • Set correct permissions for current maintainers
  • Integrate GitHub Actions for automated checks & tests
  • Apply coding best practices, e.g., code formatting
  • Move or create documentation on GitHub

Consolidate documentation

The documentation for R3BRoot is scattered over several systems:

Some of it also refers to obsolete versions (e.g., my old installation instructions for FairSoft). In my opinion, the code documentation should be as close to the code as possible. Thus, I recommend using the build-in wiki of GitHub. It is easy to use, everything is written in Markdown, and everyone has or can be given access.

I started by creating documentation on Installation and Tasks. I would ask everyone with knowledge of a specific system to write it down there.

This GitHub wiki should be restricted to code and its usage; experiment or detector specific information should probably stay in the R3B-Nustar-Wiki

Note that this will probably make www.r3broot.gsi.de obsolete. In my opinion, this is a good thing. Once it is shut down and the URL points to this repository, it is one less thing to administer and to keep up-to-date.

  • Move and update relevant documentation from www.r3broot.gsi.de to GitHub
  • Move and update relevant documentation that refers to R3BRoot coding or usage from the R3B-Nustar-Wiki to GitHub
  • Have a plan to write documentation on the relevant parts, especially for new users.
  • Discontinue www.r3broot.gsi.de.
  • Discontinue the forum, use GitHub issues or the OpenProject instead.

Clean R3BRoot Code

There is a lot of duplicated code in R3BRoot currently. One is internal duplication, which should be easy to remove with a simple abstraction. The best example for this are the dozen different fiber detectors fi*. They are almost all virtually identical in functionality. The only difference is the name. I think there should be a way to consolidate them into a template, generate the code during compilation, or create a class that simply takes the names as strings.
Some code in FairRoot was copied and renamed to R3BRoot on project creation. It might be a challenge to figure out, but some code can just be deleted and the FairRoot version used instead.

  • De-duplicate detectors, especially all the fibers.
  • Identify, test, and then remove elements that exist in FairRoot where an R3BRoot-owned version is unneccsary. Start with R3BMCStack and R3BMCTrack.

I would also argue that the base directory of R3BRoot is overfilled, to the point that one loses overview. It will get significantly better once the fibers are cleaned up. Moving all detectors into a /detectors/ folder would then significantly increase Law & Order. Doing this will probably be a major headache.

  • Move all detectors in /detectors/
    • or at least all fibers into /fibers/

There are also several points where the code is "not good enough". This is, of course, debatable to some degree. Some problems will also require hard work to fix. Here are some points that always bothered me:

  • Enable -Wall -Wextra -Wformat-security to get full information on coding problems from the compiler. Remember: The compiler is your best friend.
  • Enable static code analysis to find more problems.
  • Delete stale branches - no wait, delete every branch except dev, and make dev the new master/default.
  • Delete stuff that is no longer needed. Maybe land/?
  • Remove remains of Travis now that GitHub Actions is used for CI/CD.
  • Remove superflous comments, e.g. /* * Default constructor. * Creates an instance of the task with default parameters. */
  • Remove superflous constructors of this type: R3BSomething(const char* name, Int_t iVerbose = 1);
  • Remove functions that don't do anything, e.g R3BSomething::FinishEvent() {}
  • Check for nullptr where needed, especially in Init(), to catch wierd errors.
  • Use types, e.g. TVector3 for postitions instead of indiviual x, y, z coordinates. Especially, use std::vector<TVector3> instead of double x[20]; double y[20]; double z[20]!
  • Replace Fixed-Size C-Style arrays, especially where the input might not be fixed-size. This is a major reason for random crashes. Just use std::vector.
    Also, do not use char something[255]. Better string processing exists. To find these problems, start with searching for the regex \[\d+\].
  • Restructure overly long Exec() functions: It is not necessary to cram everything into this single function - it is a good idea to refactor functions out into easily digestible parts. This makes your life so much easier. As a good starting point, search for goto.
  • Replace Fortran components. There is no good reason to use Fortran in a C++ project. I have little domain knowledge on this topic, but a quick google search resulted in several Runge-Kutta solvers. Maybe we can adopt one of those?

run_{,aladin}_digi_test.sh.in not found

Hi,

Just merged the dev branch into my local fork and it doesn't cmake itself any more:

CMake Error: File /usr/local/FAIR/R3BRoot/macros/r3b/run_digi_test.sh.in does not exist.
CMake Error at macros/r3b/CMakeLists.txt:36 (configure_file):
configure_file Problem configuring file

and:

CMake Error: File /usr/local/FAIR/PhD_local/R3BRoot/macros/r3b/run_aladin_digi_test.sh.in does not exist.
CMake Error at macros/r3b/CMakeLists.txt:44 (configure_file):
configure_file Problem configuring file

By commenting out lines 36-39 and 44-47 the configuration will succeed (it still won't compile, but that's a separate issue which will follow in a few minutes).

Another solution would be to actually add the files to the repository so they are present...

Build fails: cannot find -lR3BLandDB

Building a fresh dev clone fails with:

Scanning dependencies of target R3BDB
Linking CXX shared library ../../lib/libR3BDB.so
/opt/rh/devtoolset-3/root/usr/libexec/gcc/x86_64-redhat-linux/4.9.1/ld: cannot find -lR3BLandDB

landdb was commented out in r3bdb/CMakeLists.txt
a37c9d5#diff-5839202420d9f765da9c1938289b795c .

I'm using FairSoft (master), FairRoot (master) with dbase (master).

Multiple conditions for skipping events based on Tpat values

I noticed there are two independent conditions for selecting events with the Tpat and they are interfering.
The first definition can be found in R3BUcesbSource.cxx, here the condition aims to eliminate meaningless events with tpat=0.:
https://github.com/R3BRootGroup/R3BRoot/blob/a558707338e1c61dc3ee83298c1f2a4b6b1fbad4/r3bsource/base/R3BUcesbSource.cxx#L292-L302

if (fSkip)
{
    if (fEventHeader->GetTpat() > 0)
    {
        FairRunOnline::Instance()->MarkFill(kTRUE);
    }
    else
    {
        FairRunOnline::Instance()->MarkFill(kFALSE);
    }
}

While in R3BTrloiiTpatReader.cxx, another condition can be found as:
https://github.com/R3BRootGroup/R3BRoot/blob/a558707338e1c61dc3ee83298c1f2a4b6b1fbad4/r3bsource/trloii/R3BTrloiiTpatReader.cxx#L102-L112

if (fTpat >= 0 && fEventHeader && fTrigger <= 0)
{
    if ((fEventHeader->GetTpat() & fTpat) == fTpat)
    {
        FairRunOnline::Instance()->MarkFill(kTRUE);
    }
    else
    {
        FairRunOnline::Instance()->MarkFill(kFALSE);
    }
}

The latter definition aims to select desired trigger condition by setting fTpat value, but when we set fSkep=true in R3BUcesbSource, it will overwrite the condition of FairRunOnline::Instance()->MarkFill(). It is not a big issue but it would be great to remove such confusion. How can we resolve this? Should we write a condition to check the fTpat value of R3BTrlolliReader in R3BUcesbSource as well as we check the fSkip value?

Hardcoded loading of boost libraries

@jose-luis-rs: Can you have a look at califa/pars/R3BCalifaGeometry.cxx and take care about following part:

// ROOT (or pyroot) is unable to automatically load dependencies of so's for whatever reason.
// so we try to force loading the lib during var initialisation.
// yes, this is ugly.
static bool _dummy_load_libboost_regex = []() {
    char buf[100];
    snprintf(buf, 100, "%s/lib/libboost_regex.so", getenv("SIMPATH"));
    return gSystem->Load(buf);
}();

This need to be fixed using dependencies in CMakeLists.txt.

Access to the Tpat/Trigger values from EventHeader

Hello everyone,

To analyze the FOOTs data taken during the beam test, I would like to make a selection on the Tpat values.
I know how to access information from the branches in TCloneArray (Mapped, Cal and Hit Data for detectors) but not from the EventHeader. I already searched in some online codes, for example R3BFootOnlineSpectra.cxx .

I extracted the root files from the lmd files in 2 ways: with the unpacker.C code so with all the Tpat values, and with online codes : /u/land/r3broot/202205_s522/foot/R3BRoot_dev/online/online_foot.C and /u/land/r3broot/202205_s522/foot/macros/online/online_foot.C .

I tried to select a specific Tpat value by using the online code but that failed so far: all events (from the lmd file) are present in the root files produced by this code, all Tpat have a unique value ( = 0) and this whatever the selected Tpat value.

On the other hand, I tried to select in the produced root files (with the unpacker.C code) a specific Tpat value by starting my attempts with the lines found in the OnlineSpectra code, but my macro crashes (*** Break *** segmentation violation ) when reaching the first new line (I checked that with cout command) :

"
FairRootManager* mgr = FairRootManager::Instance();
     if (NULL == mgr)
                     LOG(fatal) << "FairRootManager not found";

    int tpat_;
    R3BEventHeader* header;
    header = (R3BEventHeader*)mgr->GetObject("R3BEventHeader");
    if (!header)
            header = (R3BEventHeader*)mgr->GetObject("EventHeader.");

    tpat_ = header->GetTpat();
"

Thank you in advance for your help.

Califa: ClusterId

@hapol's c578178?w=1 seems to have removed the cluster id from the R3BCalifaCrystalCalData, but not from CalifaHitData.

I added that field specifically so that the clustering is easily debugable afterwards, because the user can just join R3BCalifaCrystalCalData and CalifaHitData on the clusterId to discover which hits ended up in which cluster (if any).

This allows answering questions like:

  • What is the energy weighed cluster size?
  • What are the hits ("CrystalCal") which do not end up in the cluster ("Hit") like?
  • Within a cluster, what part of the energy is in the highest energy crystal?

In retrospect, I should have called the field fDbgClusterId to make it clear that it is not providing useful data for everyday use. I did add

  // set by cal2hit so the resulting clustering decisions can be examined
  // -1: not part of any cluster

in the CrystalCal header though, making my intent clear.

As R3BCalifaHitData& operator+=( R3BCalifaCrystalCalData& cH), introduced in my commit #282 was kept in Hectors #292 except for that one line handling the id, it seems deliberate.

Either we want the user to cross check the Cal->Hit mapping. Then we should have the field in both. Or we don't (let the users hack stuff into their cal2hit if they need it), then we should get rid of the other one as well.

Cheers,
Philipp

Hard coding for fibers, tofd, and tofi

I have found some hard code files for the fiber, tofd and tofi detectors that are related to detector mappings:

  • mapping_fib30_trig.hh
  • mapping_fib31_trig.hh
  • mapping_fib32_trig.hh
  • mapping_fib33_trig.hh
  • mapping_tofd_trig.hh
  • mapping_tofi_trig.hh

This information should be managed from a mapping parameter container like the R3BCalifaMappingPar container developed for Califa. Please, don't use anymore this kind of file.

commit 9b2b2ae won't compile

Hello,
The last commit in the dev branch won't compile with gcc 5.4.0 or gcc 7.2.1
I suspect a compiler flag is missing, since the error is "language construct not recognised", on construct that are standart in C++11.

It happens on line 23 and 24 of R3BPhaseSpaceGenerator.h and line 35:
23: Bool_t Init() override;
24: Bool_t ReadEvent(FairPrimaryGenerator* primGen) override;
//...
35: ClassDefOverride(R3BPhaseSpaceGenerator, 1);

The immediately previous commit does work, and that's the one I'm using.

Cheers,
L.

Where do I post problems?

Where to write issues?

I've been working with R3BRoot since April 2021, and I am now at GSI working with the experiments. I saw that the R3BRoot website does not exist anymore, that is a shame. I also have seen that fortunately the GSI Forum still exists.

I'm a bit confused on how to act when I have questions for R3BRoot, should I add them here or on the forum? People in GSI normally just ask other elements but as you may understand, because this is a multinational collaboration, those issues should be public and anyone that runs into the same problems should be informed. In the future this will save everyone some time.

How to write issues? (if they are supposed to be here on Git)

In the future, if I want to write an issue, what information should I add at the beginning of my post? There are a lot of R3BRoot versions and people run it from different operating systems (I think everyone should do it through docker but that's another thing).

I hope this starts to change because it would be great that we can all profit from this simulation and analysis tool!

C++17 support?

I would argue for going to -std=c++17.

Most of our lx* boxes run Debian, so I will make the case for Debian.
Debian buster was released more than two years ago. It features gcc 8, which fully supports C++17.

While lxir136 still runs stretch (and to my dismay, some computers in in the counting house still run jessie!), I think of that as a reason to dist-upgrade (for security, if nothing else), not as a reason to keep the standard at the level it was a decade ago.

(A Debian fanboi myself, I will also note that Debian stable is not exactly the cutting edge. So if gcc 8 has been in stable for two years, we can be rather sure that it will also be present in all other widely used distributions.)

One alternative would be to add a recent compiler to FairSoft. FairSoft already provides versions of CMake, Perl, Boost and Python so why not gcc 12 as well? Or clang-12, if someone can figure out how to compile ROOT using that. Then we could directly go for C++20.

It should be noted that rootcint does not seem to have a flag to specify a C++ standard, it seems to use whatever root was compiled with. So departing from C++11 will require FairSoft (or at least ROOT) and FairRoot to be compiled with that flag as well.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.