Memory illegal access compiling macro in CINT

Dear Rooters,

I had compilation troubles with root using and executing a macro.
I compile the macro ‘macro.C’ with both “.x macro.C+” and “.L macro.C+”.
In both cases the first time both compilation and program execution are fined.
The second time however I have the messages:

[quote] Info in : macro_C has been modified and will be reloaded

*** Break *** segmentation violation

warning: --arch option not supported in this gdb.
/Users/gibelin/Experiments/e473s/13471: No such file or directory.
Attaching to process 13471.
Reading symbols for shared libraries . done
Reading symbols for shared libraries …
… done
0x90029f07 in wait4 ()

========== STACKS OF ALL THREADS ==========

Thread 1 (process 13471 thread 0xd03):
#0 0x90029f07 in wait4 ()
#1 0x9004723b in system ()
#2 0x010bc819 in TUnixSystem::StackTrace ()
#3 0x010c0b11 in TUnixSystem::DispatchSignals ()
#4 0x010c0c5f in SigHandler ()
#5
#6 0x01b272d4 in G__destroy_upto ()
#7 0x01b298de in G__scratch_upto_work ()
#8 0x01b29995 in G__scratch_upto ()
#9 0x01ab375a in G__unloadfile ()
#10 0x01063320 in TSystem::CompileMacro ()
#11 0x01092a5b in ScriptCompiler ()
#12 0x01ab6eb5 in G__loadfile ()
#13 0x01b03bb8 in G__process_cmd ()
#14 0x01096535 in TCint::ProcessLine ()
#15 0x0100e7b6 in TApplication::ExecuteFile ()
#16 0x0100ca0c in TApplication::ProcessLine ()
#17 0x00036476 in TRint::HandleTermInput ()
#18 0x00035bc7 in TTermInputHandler::Notify ()
#19 0x0004ee14 in TTermInputHandler::ReadNotify ()
#20 0x010c0e5e in TUnixSystem::CheckDescriptors ()
#21 0x010c106e in TUnixSystem::DispatchOneEvent ()
#22 0x0105ac95 in TSystem::InnerLoop ()
#23 0x0105de7e in TSystem::Run ()
#24 0x0100b73c in TApplication::Run ()
#25 0x00036c84 in TRint::Run ()
#26 0x00002ba3 in main ()[/quote]

For debugging purposes I simplify the program and the minimum macro that crashes is:

#include <TROOT.h>
#include <TCanvas.h>

struct TYPICAL_DATA {
  float EX,EY,TX,TY,X,Y,Z ;
} ;

void macro(){
  gROOT->GetListOfCanvases()->Delete();
  gROOT->Reset();
  TYPICAL_DATA CATS[2] ;
  TCanvas *c1 = new TCanvas("XY","TARGET",700,700);
}

If I removed the ‘struct’ definition and of course the TYPICAL_DATA CATS[2] declarations things are fine. Same if I remove the TCanvas *c1… line. I concluded that the problem might not exactly come for the structure declaration but from the array of structure that overwrite some memory.
Is it forbidden to use C like structure in compiled macros? Or is there another way to do?

I am using ROOT version 5.18/00 on Mac OS X 10.4.11

Best
Julien

gROOT->Reset SHOULD NEVER BE USED in a named macro.
This will erase declarations in includes, etc.

Rene

Dear René,

Thank you for the quick answer. My mistake.
I understand your point and it especially explains why the problem occurs at the second compilation (because the definition were erased by running the code the first time). I don’t however understand why the message is a segmentation violation and not something like: “I can not find …”.
Just to conclude this subject, I just add that I will hence use the preprocessor command defined(CINT) to be able to use gROOT->Reset () when not compiling.

I have however another problem, since this bug came while debugging another one. Please consider the following code (which also comes from simplification):

#include <TROOT.h>
#include <TCanvas.h>

void macro(){
  gROOT->GetListOfCanvases()->Delete();
#if defined(__CINT__)
  gROOT->Reset();
#endif
  TCanvas *c1 = new TCanvas("XY","TARGET",700,700); 
  TCanvas *c2 = new TCanvas("X","X"); c2->Divide(4,3);
  c1->cd();
}

Here the first execution works (w/ and w/o compilation) but the second time the CPU(s) start(s) running and the program never terminates (in reasonable times at least). Removing the ->Divide or the gROOT->GetListOfCanvases()->Delete() or c1->cd() solves the problem.

It is certainly a simple mistake but if you can point me it out.

Best
Julien

I do not see any “Divide” statement in your code.

Let me repeat once more. YOU SHOULD NEVER USE “gROOT->Reset” in a named macro,
ie in your example, you must absolutely remove the catastrophics statements

'#if defined(__CINT__) gROOT->Reset(); #endif

Rene

Dear René,

Ok I understand for the gROOT->Reset().
Now the bug I describe does appear even without this command.

Due to a bad formatting, The Divide() statement ended up at the end of the TCanvas *c2 line. So by putting every command on one line:

[code]#include <TROOT.h>
#include <TCanvas.h>

void macro(){
gROOT->GetListOfCanvases()->Delete();
TCanvas *c1 = new TCanvas(“XY”,“TARGET”,700,700);
TCanvas *c2 = new TCanvas(“X”,“X”);
c2->Divide(4,3);
c1->cd();
}
[/code]

I can execute your macro without problem on all our systems.

Rene

Dear René,

I ask one of my colleague who has a Mac OSX 10.4 and ROOT 5.15 to run the program. Same thing occurred to him: running “.x macro.C++” works fine the first time but the second time nothing appends and the CPUs start runnning at 100%.

Maybe it is a Mac problem ? I tried the same thing on a FC4 2.6.17 linux box that (unfortunately?) has a older ROOT 10.0 version and no problem occurred.

Best
Julien

I can reproduce the problem on the MAC. As a workaround replace

gROOT->GetListOfCanvases()->Delete(); by

gROOT->GetListOfCanvases()->Delete("slow");

One must be very careful when calling a collection->Delete() when the collection contains other collections. The “slow” option should be used in this case.

Rene

Thank you René. This workaround is good for me too.

Best
Julien