Support #21393

Updated by Kyle Knoepfel over 1 year ago


I am unsure if the issue tracker here is monitored. If not, I am happy to post this issue elsewhere.

I have been using gallery and have found it to be very helpful. I have a question with how gallery interacts with multiple threads.

To make the question clear I have included a minimal example reproducing the issues I have encountered. The code is an executable which reads a list of input files from the command line and opens them all in gallery.

<pre><code class="c">
#include <fstream>
#include <iostream>
#include <cstdio>
#include <cstdlib>
#include <vector>

#include <thread>
#include <TROOT.h>
#include <TThread.h>
#include "gallery/Event.h"

std::vector<std::string> filenames;

void *galleryTThread(void *inp) {
(void) inp;
for (gallery::Event ev(filenames); !ev.atEnd(); {}
return NULL;

void galleryThread() {
for (gallery::Event ev(filenames); !ev.atEnd(); {}

int main(int argc, char* argv[]) {
// Process input file definition
std::string filedef = argv[1];
std::string list_suffix = ".list";

if (std::equal(list_suffix.rbegin(), list_suffix.rend(), filedef.rbegin())) {
// File list
std::ifstream infile(filedef);
std::string filename;
while (infile >> filename) {
else {
// Files listed on command line
for (int i=optind; i<argc; i++) {


// A: works
// ROOT::EnableThreadSafety();
// galleryThread(); galleryThread(std::move(filenames));

// B: works
// std::thread t(galleryThread);
// t.join();
// C: crashes in seg fault
// ROOT::EnableThreadSafety();
// std::thread t(galleryThread);
// t.join();

// D: crashes in seg fault
// TThread t0(galleryTThread);
// t0.Run();
// t0.Join();

return 0;

As expected, (A) works. And we can even open gallery in a separate thread using (B). However, why does enabling thread safety in ROOT prevent this from working (in (C))? And what is wrong with using a TThread in (D)?

In (C) and (D), I have found that crashes seem to occur in a destructor call to the ProductIDStreamer class. Specifically, there seems to always be a vector in the ProductIDStreamer class which has an unreasonable size (I believe it must've been corrupted somehow).

Any help that could be provided on this would be greatly appreciated.