Commit 23d9eb6d authored by Alejandro Homs Puron's avatar Alejandro Homs Puron Committed by operator for beamline
Browse files

Jungfrau: add measureGainPedestal, based on AveImgProc

* Perform pedestal measurement seq in a Python thread
* Improve synchronisation around ReadHelper
parent 7b4ed52f
Pipeline #42053 failed with stages
in 6 minutes and 9 seconds
...@@ -79,7 +79,7 @@ class Jungfrau : public Model ...@@ -79,7 +79,7 @@ class Jungfrau : public Model
static constexpr MapType Type = Map32; static constexpr MapType Type = Map32;
static constexpr double DefaultCoeffs[3][2] = { static constexpr double DefaultCoeffs[3][2] = {
{ 0.999952, 0.4}, // effectively {1, 0} { 0.999952, 0.4}, // effectively {1, 0}
{ -26.144935, 394047.3}, // G0 x16 { -26.144935, 394047.3}, // G0 x26
{-368.163215, 5531211.9}, // G1 x14 {-368.163215, 5531211.9}, // G1 x14
}; };
static constexpr Data::TYPE DataType = Data::UINT32; static constexpr Data::TYPE DataType = Data::UINT32;
...@@ -177,10 +177,13 @@ class Jungfrau : public Model ...@@ -177,10 +177,13 @@ class Jungfrau : public Model
void readGainADCMaps(Data& gain_map, Data& adc_map, FrameType& frame); void readGainADCMaps(Data& gain_map, Data& adc_map, FrameType& frame);
void readGainPedProcMap(Data& proc_map, FrameType& frame); void readGainPedProcMap(Data& proc_map, FrameType& frame);
void readAveMap(Data& ave_map, FrameType& nb_frames, FrameType& frame);
void setGainPedMapType(GainPed::MapType map_type); void setGainPedMapType(GainPed::MapType map_type);
void getGainPedMapType(GainPed::MapType& map_type); void getGainPedMapType(GainPed::MapType& map_type);
void setGainPedCalib(const GainPed::Calib& calib)
{ m_gain_ped_img_proc->m_gain_ped.setCalib(calib); }
void getGainPedCalib(GainPed::Calib& calib) void getGainPedCalib(GainPed::Calib& calib)
{ m_gain_ped_img_proc->m_gain_ped.getCalib(calib); } { m_gain_ped_img_proc->m_gain_ped.getCalib(calib); }
...@@ -318,51 +321,98 @@ class Jungfrau : public Model ...@@ -318,51 +321,98 @@ class Jungfrau : public Model
typedef std::vector<ImgProcBase *> ImgProcList; typedef std::vector<ImgProcBase *> ImgProcList;
template <class T> template <class T>
class ReaderHelper : public Buffer::Callback { class ReadHelper : public Buffer::Callback {
DEB_CLASS_NAMESPC(DebModCamera, "Jungfrau::ReaderHelper", DEB_CLASS_NAMESPC(DebModCamera, "Jungfrau::ReadHelper",
"SlsDetector"); "SlsDetector");
public: public:
typedef DoubleBuffer<T> DBuffer; typedef DoubleBuffer<T> DBuffer;
typedef DoubleBufferReader<T> DBufferReader;
T& addRead(DBuffer& b, FrameType& frame) { class Reader : public DBufferReader {
DEB_MEMBER_FUNCT(); DEB_CLASS_NAMESPC(DebModCamera,
if (m_reader) "Jungfrau::ReadHelper::Reader",
THROW_HW_ERROR(Error) "SlsDetector");
<< "A reader is already active"; public:
m_reader = new Reader(b, frame); Reader(DBuffer& db, FrameType f, ReadHelper *h)
frame = m_reader->getCounter(); : DBufferReader(db, f), m_helper(h)
return m_reader->getBuffer(); { DEB_CONSTRUCTOR(); }
}
~Reader()
{ DEB_DESTRUCTOR(); }
void addData(Data& src, Data& ref) { void addData(Data& src, Data& ref) {
DEB_MEMBER_FUNCT(); DEB_MEMBER_FUNCT();
makeDataRef(src, ref, this); makeDataRef(src, ref, m_helper);
m_buffer_list.insert(ref.data()); m_buffer_list.insert(ref.data());
DEB_TRACE() << DEB_VAR1(m_buffer_list.size()); DEB_TRACE() << DEB_VAR1(m_buffer_list.size());
} }
protected: private:
virtual void destroy(void *buffer) { friend class ReadHelper;
typedef std::set<void *> BufferList;
std::pair<bool, bool> destroy(void *buffer) {
DEB_MEMBER_FUNCT(); DEB_MEMBER_FUNCT();
DEB_PARAM() << DEB_VAR1(m_buffer_list.size()); DEB_PARAM() << DEB_VAR1(m_buffer_list.size());
if (m_buffer_list.empty() || !m_reader) typedef typename BufferList::iterator BufferIt;
DEB_ERROR() << "Unexpected " BufferIt it, end = m_buffer_list.end();
<< DEB_VAR1(buffer);
BufferList::iterator it, end = m_buffer_list.end();
it = find(m_buffer_list.begin(), end, buffer); it = find(m_buffer_list.begin(), end, buffer);
if (it == end) bool found = (it != end);
DEB_ERROR() << "Bad " << DEB_VAR1(buffer); if (found)
m_buffer_list.erase(it); m_buffer_list.erase(it);
if (m_buffer_list.empty()) return {found, m_buffer_list.empty()};
m_reader = NULL; }
ReadHelper *m_helper;
BufferList m_buffer_list;
};
~ReadHelper() {
DEB_DESTRUCTOR();
AutoMutex l(m_mutex);
while (!m_reader_list.empty())
deleteReader(m_reader_list.begin(), l);
}
Reader *addRead(DBuffer& b, FrameType& frame) {
DEB_MEMBER_FUNCT();
Reader *r = new Reader(b, frame, this);
frame = r->getCounter();
AutoMutex l(m_mutex);
m_reader_list.insert(r);
return r;
}
protected:
virtual void destroy(void *buffer) {
DEB_MEMBER_FUNCT();
AutoMutex l(m_mutex);
ReaderIt it, end = m_reader_list.end();
for (it = m_reader_list.begin(); it != end; ++it) {
auto [found, empty] = (*it)->destroy(buffer);
if (!found)
continue;
else if (empty)
deleteReader(it, l);
return;
}
DEB_ERROR() << "Bad " << DEB_VAR1(buffer);
} }
private: private:
typedef DoubleBufferReader<T> Reader; typedef std::set<Reader *> ReaderList;
typedef std::set<void *> BufferList; typedef typename ReaderList::iterator ReaderIt;
AutoPtr<Reader> m_reader; void deleteReader(ReaderIt it, AutoMutex& l) {
BufferList m_buffer_list; DEB_MEMBER_FUNCT();
Reader *r = *it;
m_reader_list.erase(it);
AutoMutexUnlock u(l);
delete r;
}
Mutex m_mutex;
ReaderList m_reader_list;
}; };
class GainADCMapImgProc : public ImgProcBase class GainADCMapImgProc : public ImgProcBase
...@@ -398,11 +448,11 @@ class Jungfrau : public Model ...@@ -398,11 +448,11 @@ class Jungfrau : public Model
} }
}; };
typedef ReaderHelper<MapData> Reader; typedef ReadHelper<MapData> Helper;
typedef typename Reader::DBuffer DBuffer; typedef typename Helper::DBuffer DBuffer;
DBuffer m_buffer; DBuffer m_buffer;
AutoPtr<Reader> m_reader; AutoPtr<Helper> m_helper;
}; };
class GainPedImgProc : public ImgProcBase class GainPedImgProc : public ImgProcBase
...@@ -432,11 +482,50 @@ class Jungfrau : public Model ...@@ -432,11 +482,50 @@ class Jungfrau : public Model
void clear() { clearData(proc_map); } void clear() { clearData(proc_map); }
}; };
typedef ReaderHelper<MapData> Reader; typedef ReadHelper<MapData> Helper;
typedef typename Reader::DBuffer DBuffer; typedef typename Helper::DBuffer DBuffer;
DBuffer m_buffer; DBuffer m_buffer;
AutoPtr<Reader> m_reader; AutoPtr<Helper> m_helper;
};
class AveImgProc : public ImgProcBase
{
DEB_CLASS_NAMESPC(DebModCamera, "Jungfrau::AveImgProc",
"SlsDetector");
public:
AveImgProc(Jungfrau *jungfrau);
virtual void updateImageSize(Size size, bool raw);
virtual void clear();
virtual void processFrame(Data& data);
void readAveMap(Data& ave_map, FrameType& nb_frames,
FrameType& frame);
private:
template <class M>
void processFrameFunct(Data& data);
struct MapData {
Data ave_map;
FrameType nb_frames;
MapData() { ave_map.type = Data::DOUBLE; }
void updateSize(Size size) {
updateDataSize(ave_map, size);
};
void clear() { clearData(ave_map); }
};
typedef ReadHelper<MapData> Helper;
typedef typename Helper::DBuffer DBuffer;
DBuffer m_buffer;
AutoPtr<Helper> m_helper;
Data m_acc;
int m_nb_frames;
}; };
class ModelReconstruction : public SlsDetector::Reconstruction class ModelReconstruction : public SlsDetector::Reconstruction
...@@ -472,7 +561,9 @@ class Jungfrau : public Model ...@@ -472,7 +561,9 @@ class Jungfrau : public Model
} }
static void clearData(Data& d) { static void clearData(Data& d) {
memset(d.data(), 0, d.size()); void *p = d.data();
if (p)
memset(p, 0, d.size());
} }
static void makeDataRef(Data& src, Data& ref, Buffer::Callback *cb) { static void makeDataRef(Data& src, Data& ref, Buffer::Callback *cb) {
...@@ -506,6 +597,15 @@ class Jungfrau : public Model ...@@ -506,6 +597,15 @@ class Jungfrau : public Model
void removeAllImgProc(); void removeAllImgProc();
void doSetImgProcConfig(std::string config, bool force); void doSetImgProcConfig(std::string config, bool force);
Data getRawData(Data& data)
{
if (m_img_src == Raw)
return data;
BufferMgr *buffer_mgr = getBuffer();
BufferCtrlObj *buffer = buffer_mgr->getBufferCtrlObj(AcqBuffer);
return buffer->getFrameData(data.frameNumber);
}
int getNbJungfrauModules() int getNbJungfrauModules()
{ return getNbDetModules(); } { return getNbDetModules(); }
...@@ -535,6 +635,7 @@ class Jungfrau : public Model ...@@ -535,6 +635,7 @@ class Jungfrau : public Model
Cond m_cond; Cond m_cond;
AutoPtr<GainPedImgProc> m_gain_ped_img_proc; AutoPtr<GainPedImgProc> m_gain_ped_img_proc;
AutoPtr<GainADCMapImgProc> m_gain_adc_map_img_proc; AutoPtr<GainADCMapImgProc> m_gain_adc_map_img_proc;
AutoPtr<AveImgProc> m_ave_img_proc;
std::string m_img_proc_config; std::string m_img_proc_config;
ImgProcList m_img_proc_list; ImgProcList m_img_proc_list;
ImgSrc m_img_src; ImgSrc m_img_src;
......
...@@ -177,10 +177,13 @@ class Jungfrau : public SlsDetector::Model ...@@ -177,10 +177,13 @@ class Jungfrau : public SlsDetector::Model
void readGainPedProcMap(Data& proc_map /Out/, void readGainPedProcMap(Data& proc_map /Out/,
unsigned long& frame /In,Out/); unsigned long& frame /In,Out/);
void readAveMap(Data& proc_map /Out/, unsigned long& nb_frames /Out/,
unsigned long& frame /In,Out/);
void setGainPedMapType(Jungfrau::GainPed::MapType map_type); void setGainPedMapType(Jungfrau::GainPed::MapType map_type);
void getGainPedMapType(Jungfrau::GainPed::MapType& map_type /Out/); void getGainPedMapType(Jungfrau::GainPed::MapType& map_type /Out/);
void setGainPedCalib(const SlsDetector::Jungfrau::GainPed::Calib& calib);
void getGainPedCalib(SlsDetector::Jungfrau::GainPed::Calib& calib /Out/); void getGainPedCalib(SlsDetector::Jungfrau::GainPed::Calib& calib /Out/);
void setImgSrc(Jungfrau::ImgSrc img_src); void setImgSrc(Jungfrau::ImgSrc img_src);
......
...@@ -368,19 +368,10 @@ void Jungfrau::ImgProcTask::process(Data& data) ...@@ -368,19 +368,10 @@ void Jungfrau::ImgProcTask::process(Data& data)
DEB_PARAM() << DEB_VAR2(data.frameNumber, data.data()); DEB_PARAM() << DEB_VAR2(data.frameNumber, data.data());
Data src;
if (m_jungfrau->m_img_src == Raw) {
src = data;
} else {
BufferMgr *buffer_mgr = m_jungfrau->getBuffer();
BufferCtrlObj *buffer = buffer_mgr->getBufferCtrlObj(AcqBuffer);
src = buffer->getFrameData(data.frameNumber);
}
ImgProcList& img_proc_list = m_jungfrau->m_img_proc_list; ImgProcList& img_proc_list = m_jungfrau->m_img_proc_list;
ImgProcList::iterator it, end = img_proc_list.end(); ImgProcList::iterator it, end = img_proc_list.end();
for (it = img_proc_list.begin(); it != end; ++it) for (it = img_proc_list.begin(); it != end; ++it)
(*it)->processFrame(src); (*it)->processFrame(data);
} }
...@@ -437,7 +428,7 @@ void Jungfrau::ImgProcBase::clear() ...@@ -437,7 +428,7 @@ void Jungfrau::ImgProcBase::clear()
*/ */
Jungfrau::GainADCMapImgProc::GainADCMapImgProc(Jungfrau *jungfrau) Jungfrau::GainADCMapImgProc::GainADCMapImgProc(Jungfrau *jungfrau)
: ImgProcBase(jungfrau, "gain_adc_map"), m_reader(new Reader) : ImgProcBase(jungfrau, "gain_adc_map"), m_helper(new Helper)
{ {
DEB_CONSTRUCTOR(); DEB_CONSTRUCTOR();
} }
...@@ -468,19 +459,21 @@ void Jungfrau::GainADCMapImgProc::processFrame(Data& data) ...@@ -468,19 +459,21 @@ void Jungfrau::GainADCMapImgProc::processFrame(Data& data)
long frame = data.frameNumber; long frame = data.frameNumber;
DEB_PARAM() << DEB_VAR1(frame); DEB_PARAM() << DEB_VAR1(frame);
Data raw = m_jungfrau->getRawData(data);
DoubleBufferWriter<MapData> w(m_buffer); DoubleBufferWriter<MapData> w(m_buffer);
MapData& m = w.getBuffer(); MapData& m = w.getBuffer();
DEB_TRACE() << DEB_VAR1(&m); DEB_TRACE() << DEB_VAR1(&m);
unsigned short *src; unsigned short *src;
{ {
src = (unsigned short *) data.data(); src = (unsigned short *) raw.data();
unsigned char *dst = (unsigned char *) m.gain_map.data(); unsigned char *dst = (unsigned char *) m.gain_map.data();
for (int i = 0; i < m_pixels; ++i, ++src, ++dst) for (int i = 0; i < m_pixels; ++i, ++src, ++dst)
*dst = *src >> 14; *dst = *src >> 14;
m.gain_map.frameNumber = frame; m.gain_map.frameNumber = frame;
} }
{ {
src = (unsigned short *) data.data(); src = (unsigned short *) raw.data();
unsigned short *dst = (unsigned short *) m.adc_map.data(); unsigned short *dst = (unsigned short *) m.adc_map.data();
for (int i = 0; i < m_pixels; ++i, ++src, ++dst) for (int i = 0; i < m_pixels; ++i, ++src, ++dst)
*dst = *src & 0x3fff; *dst = *src & 0x3fff;
...@@ -494,9 +487,10 @@ void Jungfrau::GainADCMapImgProc::readGainADCMaps(Data& gain_map, Data& adc_map, ...@@ -494,9 +487,10 @@ void Jungfrau::GainADCMapImgProc::readGainADCMaps(Data& gain_map, Data& adc_map,
{ {
DEB_MEMBER_FUNCT(); DEB_MEMBER_FUNCT();
DEB_PARAM() << DEB_VAR1(frame); DEB_PARAM() << DEB_VAR1(frame);
MapData &m = m_reader->addRead(m_buffer, frame); Helper::Reader *r = m_helper->addRead(m_buffer, frame);
m_reader->addData(m.gain_map, gain_map); MapData &m = r->getBuffer();
m_reader->addData(m.adc_map, adc_map); r->addData(m.gain_map, gain_map);
r->addData(m.adc_map, adc_map);
DEB_RETURN() << DEB_VAR3(gain_map, adc_map, frame); DEB_RETURN() << DEB_VAR3(gain_map, adc_map, frame);
} }
...@@ -506,7 +500,7 @@ void Jungfrau::GainADCMapImgProc::readGainADCMaps(Data& gain_map, Data& adc_map, ...@@ -506,7 +500,7 @@ void Jungfrau::GainADCMapImgProc::readGainADCMaps(Data& gain_map, Data& adc_map,
Jungfrau::GainPedImgProc::GainPedImgProc(Jungfrau *jungfrau) Jungfrau::GainPedImgProc::GainPedImgProc(Jungfrau *jungfrau)
: ImgProcBase(jungfrau, "gain_ped"), m_gain_ped(jungfrau), : ImgProcBase(jungfrau, "gain_ped"), m_gain_ped(jungfrau),
m_reader(new Reader) m_helper(new Helper)
{ {
DEB_CONSTRUCTOR(); DEB_CONSTRUCTOR();
} }
...@@ -547,10 +541,12 @@ void Jungfrau::GainPedImgProc::processFrame(Data& data) ...@@ -547,10 +541,12 @@ void Jungfrau::GainPedImgProc::processFrame(Data& data)
long frame = data.frameNumber; long frame = data.frameNumber;
DEB_PARAM() << DEB_VAR1(frame); DEB_PARAM() << DEB_VAR1(frame);
Data raw = m_jungfrau->getRawData(data);
DoubleBufferWriter<MapData> w(m_buffer); DoubleBufferWriter<MapData> w(m_buffer);
MapData& m = w.getBuffer(); MapData& m = w.getBuffer();
DEB_TRACE() << DEB_VAR1(&m); DEB_TRACE() << DEB_VAR1(&m);
m_gain_ped.processFrame(data, m.proc_map); m_gain_ped.processFrame(raw, m.proc_map);
m.proc_map.frameNumber = frame; m.proc_map.frameNumber = frame;
w.setCounter(frame); w.setCounter(frame);
} }
...@@ -559,11 +555,97 @@ void Jungfrau::GainPedImgProc::readProcMap(Data& proc_map, FrameType& frame) ...@@ -559,11 +555,97 @@ void Jungfrau::GainPedImgProc::readProcMap(Data& proc_map, FrameType& frame)
{ {
DEB_MEMBER_FUNCT(); DEB_MEMBER_FUNCT();
DEB_PARAM() << DEB_VAR1(frame); DEB_PARAM() << DEB_VAR1(frame);
MapData &m = m_reader->addRead(m_buffer, frame); Helper::Reader *r = m_helper->addRead(m_buffer, frame);
m_reader->addData(m.proc_map, proc_map); MapData &m = r->getBuffer();
r->addData(m.proc_map, proc_map);
DEB_RETURN() << DEB_VAR2(proc_map, frame); DEB_RETURN() << DEB_VAR2(proc_map, frame);
} }
/*
* Jungfrau::AveImgProc class
*/
Jungfrau::AveImgProc::AveImgProc(Jungfrau *jungfrau)
: ImgProcBase(jungfrau, "ave"), m_helper(new Helper), m_nb_frames(0)
{
DEB_CONSTRUCTOR();
m_acc.type = Data::UINT32;
}
void Jungfrau::AveImgProc::updateImageSize(Size size, bool raw)
{
DEB_MEMBER_FUNCT();
DEB_PARAM() << DEB_VAR3(m_name, size, raw);
ImgProcBase::updateImageSize(size, raw);
for (auto& d : m_buffer)
d.updateSize(size);
updateDataSize(m_acc, size);
}
void Jungfrau::AveImgProc::clear()
{
DEB_MEMBER_FUNCT();
ImgProcBase::clear();
for (auto& d : m_buffer)
d.clear();
m_buffer.reset();
clearData(m_acc);
m_nb_frames = 0;
}
template <class M>
void Jungfrau::AveImgProc::processFrameFunct(Data& data)
{
DEB_MEMBER_FUNCT();
long frame = data.frameNumber;
DEB_PARAM() << DEB_VAR1(frame);
DoubleBufferWriter<MapData> w(m_buffer);
MapData& m = w.getBuffer();
DEB_TRACE() << DEB_VAR1(&m);
++m_nb_frames;
using S = typename M::Pixel;
S *src = (S *) data.data();
unsigned int *acc = (unsigned int *) m_acc.data();
double *ave = (double *) m.ave_map.data();
for (int i = 0; i < m_pixels; ++i, ++src, ++acc, ++ave) {
*acc += *src;
*ave = *acc / m_nb_frames;
}
m.ave_map.frameNumber = frame;
m.nb_frames = m_nb_frames;
w.setCounter(frame);
}
void Jungfrau::AveImgProc::processFrame(Data& data)
{
DEB_MEMBER_FUNCT();
GainPed& gain_ped = m_jungfrau->m_gain_ped_img_proc->m_gain_ped;
GainPed::MapType map_type;
gain_ped.getMapType(map_type);
if (map_type == GainPed::Map16)
processFrameFunct<GainPed::Map16Data>(data);
else
processFrameFunct<GainPed::Map32Data>(data);
}
void Jungfrau::AveImgProc::readAveMap(Data& ave_map, FrameType& nb_frames,
FrameType& frame)
{
DEB_MEMBER_FUNCT();
DEB_PARAM() << DEB_VAR1(frame);
Helper::Reader *r = m_helper->addRead(m_buffer, frame);
MapData &m = r->getBuffer();
r->addData(m.ave_map, ave_map);
nb_frames = m.nb_frames;
DEB_RETURN() << DEB_VAR3(ave_map, nb_frames, frame);
}
/* /*
* Jungfrau::ModelReconstruction class * Jungfrau::ModelReconstruction class
*/ */
...@@ -612,6 +694,7 @@ Jungfrau::Jungfrau(Camera *cam) ...@@ -612,6 +694,7 @@ Jungfrau::Jungfrau(Camera *cam)
m_gain_ped_img_proc = new GainPedImgProc(this); m_gain_ped_img_proc = new GainPedImgProc(this);
m_gain_adc_map_img_proc = new GainADCMapImgProc(this); m_gain_adc_map_img_proc = new GainADCMapImgProc(this);
m_ave_img_proc = new AveImgProc(this);
m_reconstruction = new ModelReconstruction(this); m_reconstruction = new ModelReconstruction(this);
...@@ -913,6 +996,7 @@ void Jungfrau::updateImageSize() ...@@ -913,6 +996,7 @@ void Jungfrau::updateImageSize()
m_gain_ped_img_proc->updateImageSize(size, raw); m_gain_ped_img_proc->updateImageSize(size, raw);
m_gain_adc_map_img_proc->updateImageSize(size, raw); m_gain_adc_map_img_proc->updateImageSize(size, raw);
m_ave_img_proc->updateImageSize(size, raw);
} }
bool Jungfrau::checkSettings(Settings settings) bool Jungfrau::checkSettings(Settings settings)
...@@ -1209,6 +1293,15 @@ void Jungfrau::doSetImgProcConfig(std::string config, bool force) ...@@ -1209,6 +1293,15 @@ void Jungfrau::doSetImgProcConfig(std::string config, bool force)
DEB_TRACE() << "Adding gain_adc_map"; DEB_TRACE() << "Adding gain_adc_map";
img_proc_list.push_back(m_gain_adc_map_img_proc); img_proc_list.push_back(m_gain_adc_map_img_proc);
} }
if (checkConfigAndDelete("ave")) {
if (m_img_src == GainPedCorr) {
DEB_TRACE() << "Adding ave";
img_proc_list.push_back(m_ave_img_proc);
} else {
DEB_TRACE() << "Ignoring ave";
m_ave_img_proc->clear();
}
}
if (!config_list.empty()) if (!config_list.empty())
THROW_HW_ERROR(InvalidValue) << "Invalid " << DEB_VAR1(config); THROW_HW_ERROR(InvalidValue) << "Invalid " << DEB_VAR1(config);