ATLAS Offline Software
Public Types | Public Member Functions | Static Public Member Functions | Public Attributes | Private Member Functions | List of all members
SG::PyProxyMgr Struct Reference

A helper class to manage accesses to PyProxies. More...

#include <SgPyDataModel.h>

Collaboration diagram for SG::PyProxyMgr:

Public Types

typedef std::unordered_map< StoreGateSvc *, SG::PyProxyDict * > PyProxyMap_t
 
typedef std::unordered_map< CLID, std::string > ClidMap_t
 a dictionary of CLID -> reflex typename More...
 

Public Member Functions

 PyProxyMgr ()
 
 ~PyProxyMgr ()
 
SG::PyProxyDictpyproxy (StoreGateSvc *sg)
 
PyObjectpyclid (PyObject *tp)
 returns a borrowed reference More...
 
PyObjectpytp (PyObject *clid)
 returns a borrowed reference More...
 
PyObjectpytp (CLID clid)
 returns a borrowed reference More...
 
CLID clid (PyObject *tp)
 
CLID clid_from_tid (PyObject *tp)
 
const char * load_type (CLID id)
 ensure everything has been loaded for the clid id (classid, reflex dict, baseinfobase,...) More...
 

Static Public Member Functions

static PyProxyMgrinstance ()
 

Public Attributes

IDictLoaderSvcm_dictSvc
 
IClassIDSvc * m_clidSvc
 
PyObjectm_aliases
 a dictionary of "typedef'ed typename" -> "typename" More...
 
PyObjectm_clids
 a dictionary of 'typename' -> CLID (and reverse CLID->'typename') More...
 
PyProxyMap_t m_proxyMap
 
ClidMap_t m_clidMap
 

Private Member Functions

PyObjectimportDictAliases ()
 import the dictionary of aliases from a well known location More...
 

Detailed Description

A helper class to manage accesses to PyProxies.

Definition at line 191 of file SgPyDataModel.h.

Member Typedef Documentation

◆ ClidMap_t

typedef std::unordered_map<CLID, std::string> SG::PyProxyMgr::ClidMap_t

a dictionary of CLID -> reflex typename

Definition at line 205 of file SgPyDataModel.h.

◆ PyProxyMap_t

Definition at line 201 of file SgPyDataModel.h.

Constructor & Destructor Documentation

◆ PyProxyMgr()

SG::PyProxyMgr::PyProxyMgr ( )

Definition at line 165 of file SgPyDataModel.cxx.

166  {
168  m_clids = PyDict_New();
169  m_clidSvc = 0;
170  {
171  ServiceHandle<IClassIDSvc> svc("ClassIDSvc", "SgPyDataModel");
172  if ( !svc.retrieve().isSuccess()) {
173  throw std::runtime_error
174  ("SG::PyProxyMgr: Could not retrieve ClassIDSvc");
175  }
176  m_clidSvc = svc.operator->();
177  }
178  m_dictSvc = 0;
179  {
180  ServiceHandle<IDictLoaderSvc> svc("AthDictLoaderSvc", "SgPyDataModel");
181  if ( !svc.retrieve().isSuccess()) {
182  throw std::runtime_error
183  ("SG::PyProxyMgr: Could not retrieve AthDictLoaderSvc");
184  }
185  m_dictSvc = svc.operator->();
186  }
187  }

◆ ~PyProxyMgr()

SG::PyProxyMgr::~PyProxyMgr ( )

Definition at line 189 of file SgPyDataModel.cxx.

190  {
191  // Don't do this if don't have a valid thread state.
192  // (With py3, the interpreter gets shut down before global dtors run...)
193  if (_PyThreadState_UncheckedGet())
194  {
195  Py_DECREF(m_aliases);
196  Py_DECREF(m_clids);
197  }
198  // delete the proxy dicts...
200  i = m_proxyMap.begin(),
201  iEnd = m_proxyMap.end();
202  i != iEnd;
203  ++i ) {
204  delete i->second; i->second = 0;
205  }
206  }

Member Function Documentation

◆ clid()

CLID SG::PyProxyMgr::clid ( PyObject tp)
inline

Definition at line 274 of file SgPyDataModel.h.

275  {
276  CLID id = CLID_NULL;
277  // FIXME: get rid of this massaging when/if ROOT finally
278  // standardize on keeping the std:: namespace...
279  std::string tpstr = RootUtils::PyGetString(tp).first;
280  std::string tn;
281  {
282  // Protect against data race inside TClassEdit.
283  // https://github.com/root-project/root/issues/10353
284  // Should be fixed in root 6.26.02.
285  R__WRITE_LOCKGUARD(ROOT::gCoreMutex);
286  tn = TClassEdit::ShortType(tpstr.c_str(),
287  TClassEdit::kDropAllDefault);
288  }
289  m_clidSvc->getIDOfTypeName(tn, id).ignore();
290  if ( id == CLID_NULL ) {
291  // try an alias...
292  PyObject* alias = PyDict_GetItemString(m_aliases, tn.c_str());
293  if ( alias ){
294  std::string aliasstr = RootUtils::PyGetString(alias).first;
295  m_clidSvc->getIDOfTypeName(aliasstr, id).ignore();
296  }
297  }
298  if (id == CLID_NULL) {
299  // then try a type-id name...
300  return this->clid_from_tid (tp);
301  }
302  return id;
303  }

◆ clid_from_tid()

CLID SG::PyProxyMgr::clid_from_tid ( PyObject tp)
inline

Definition at line 306 of file SgPyDataModel.h.

307  {
308  CLID id = CLID_NULL;
309  // FIXME: get rid of this massaging when/if ROOT finally
310  // standardize on keeping the std:: namespace...
311  std::string tpstr = RootUtils::PyGetString(tp).first;
312  std::string tn;
313  {
314  // Protect against data race inside TClassEdit.
315  // https://github.com/root-project/root/issues/10353
316  // Should be fixed in root 6.26.02.
317  R__WRITE_LOCKGUARD(ROOT::gCoreMutex);
318  tn = TClassEdit::ShortType(tpstr.c_str(),
319  TClassEdit::kDropAllDefault);
320  }
321  m_clidSvc->getIDOfTypeInfoName(tn, id).ignore();
322  if ( id == CLID_NULL ) {
323  // try an alias...
324  PyObject* alias = PyDict_GetItemString(m_aliases, tn.c_str());
325  if ( alias ){
326  std::string aliasstr = RootUtils::PyGetString(alias).first;
327  m_clidSvc->getIDOfTypeInfoName(aliasstr,
328  id).ignore();
329  }
330  }
331  return id;
332  }

◆ importDictAliases()

PyObject* SG::PyProxyMgr::importDictAliases ( )
inlineprivate

import the dictionary of aliases from a well known location

Definition at line 369 of file SgPyDataModel.h.

370  {
371  const std::string moduleName = "AthenaPython.Bindings";
372  PyObject* module = PyImport_ImportModule
373  ( const_cast<char*>(moduleName.c_str()) );
374  if ( !module || !PyModule_Check(module) ) {
375  std::cerr << "SG::PyProxyDict WARNING: could not import module '"
376  << moduleName << "' !\n";
377  Py_XDECREF(module);
378  m_aliases = PyDict_New();
379  return m_aliases;
380  }
381 
382  m_aliases = PyDict_GetItemString(PyModule_GetDict(module),
383  (char*)"_clid_typename_aliases");
384  // borrowed ref. so we increment it
385  Py_XINCREF(m_aliases);
386  // don't need this one anymore
387  Py_DECREF(module);
388 
389  if ( !m_aliases ) {
390  std::cerr << "SG::PyProxyDict WARNING: could not retrieve the "
391  << "dictionary of aliases from '"
392  << moduleName << "' !\n";
393  Py_XDECREF(m_aliases);
394  m_aliases = PyDict_New();
395  }
396  return m_aliases;
397  }

◆ instance()

static PyProxyMgr& SG::PyProxyMgr::instance ( )
inlinestatic

Definition at line 209 of file SgPyDataModel.h.

210  { static PyProxyMgr mgr; return mgr; }

◆ load_type()

const char* SG::PyProxyMgr::load_type ( CLID  id)
inline

ensure everything has been loaded for the clid id (classid, reflex dict, baseinfobase,...)

Returns
the reflex typename associated with that clid

Definition at line 339 of file SgPyDataModel.h.

340  {
341  typedef ClidMap_t::iterator Itr_t;
342  Itr_t i = m_clidMap.find(id);
343  if (i != m_clidMap.end()) {
344  return i->second.c_str();
345  }
346  // Reflex now returns std::basic_string<char> instead of std::string
347  std::string tname = m_dictSvc->load_type(id).Name(Reflex::SCOPED);
348  // handle '> >'. order MATTERS!
349  ::cxx_replace(tname, "basic_string<char> >", "string>");
350  ::cxx_replace(tname, "basic_string<char>", "string");
351  m_clidMap[id] = tname;
352 
353  // Try to make sure the BIB is initialized.
354  std::string bibname = "SG::BaseInfo<" + tname + ">";
355  TClass* bibcl = gROOT->GetClass (bibname.c_str());
356  if (bibcl) {
357  TMethod* m = bibcl->GetMethodAny ("baseinfo");
358  if (m) {
359  TMethodCall call (m);
360  call.Execute();
361  }
362  }
363 
364  return m_clidMap[id].c_str();
365  }

◆ pyclid()

PyObject* SG::PyProxyMgr::pyclid ( PyObject tp)
inline

returns a borrowed reference

Definition at line 219 of file SgPyDataModel.h.

220  {
221  PyObject* clid = PyDict_GetItem(m_clids, tp);
222  if ( NULL == clid ) {
223  const CLID id = this->clid(tp);
224  if ( id == CLID_NULL ) {
225  return NULL;
226  }
227  clid = PyLong_FromLong(id);
228  PyDict_SetItem(m_clids, tp, clid);
229  // add reverse look-up entry too
230  PyDict_SetItem(m_clids, clid, tp);
231  //Py_INCREF(clid);
232  }
233  return clid;
234  }

◆ pyproxy()

PyProxyDict * SG::PyProxyMgr::pyproxy ( StoreGateSvc sg)
inline

Definition at line 462 of file SgPyDataModel.h.

463  {
464  SG::PyProxyDict* p = 0;
466  if ( i == m_proxyMap.end() ) {
467  m_proxyMap[sg] = p = new SG::PyProxyDict(sg);
468  } else {
469  p = i->second;
470  }
471  return p;
472  }

◆ pytp() [1/2]

PyObject* SG::PyProxyMgr::pytp ( CLID  clid)
inline

returns a borrowed reference

Definition at line 265 of file SgPyDataModel.h.

266  {
267  PyObject* pyclid = PyLong_FromLong(clid);
268  PyObject* o = this->pytp(pyclid);
269  Py_DECREF(pyclid);
270  return o;
271  }

◆ pytp() [2/2]

PyObject* SG::PyProxyMgr::pytp ( PyObject clid)
inline

returns a borrowed reference

Definition at line 238 of file SgPyDataModel.h.

239  {
240  PyObject* tp = PyDict_GetItem(m_clids, clid);
241  if ( NULL == tp ) {
242  std::string cpp_tp;
243  if (!m_clidSvc->getTypeNameOfID(PyLong_AsUnsignedLong(clid),
244  cpp_tp).isSuccess()) {
245  return NULL;
246  }
247  PyObject* alias = PyDict_GetItemString(m_aliases, cpp_tp.c_str());
248  if ( alias ) {
249  tp = alias;
250  } else {
251  tp = PyUnicode_FromString(cpp_tp.c_str());
252  }
253  PyDict_SetItem(m_clids, clid, tp);
254  // reverse look-up
255  PyDict_SetItem(m_clids, tp, clid);
256  if (!alias) {
257  Py_DECREF(tp);
258  }
259  }
260  return tp;
261  }

Member Data Documentation

◆ m_aliases

PyObject* SG::PyProxyMgr::m_aliases

a dictionary of "typedef'ed typename" -> "typename"

Definition at line 196 of file SgPyDataModel.h.

◆ m_clidMap

ClidMap_t SG::PyProxyMgr::m_clidMap

Definition at line 206 of file SgPyDataModel.h.

◆ m_clids

PyObject* SG::PyProxyMgr::m_clids

a dictionary of 'typename' -> CLID (and reverse CLID->'typename')

Definition at line 199 of file SgPyDataModel.h.

◆ m_clidSvc

IClassIDSvc* SG::PyProxyMgr::m_clidSvc

Definition at line 194 of file SgPyDataModel.h.

◆ m_dictSvc

IDictLoaderSvc* SG::PyProxyMgr::m_dictSvc

Definition at line 193 of file SgPyDataModel.h.

◆ m_proxyMap

PyProxyMap_t SG::PyProxyMgr::m_proxyMap

Definition at line 202 of file SgPyDataModel.h.


The documentation for this struct was generated from the following files:
xAOD::iterator
JetConstituentVector::iterator iterator
Definition: JetConstituentVector.cxx:68
python.SystemOfUnits.m
int m
Definition: SystemOfUnits.py:91
SG::PyProxyMgr::m_dictSvc
IDictLoaderSvc * m_dictSvc
Definition: SgPyDataModel.h:193
ParticleTest.tp
tp
Definition: ParticleTest.py:25
SG::PyProxyMgr::m_aliases
PyObject * m_aliases
a dictionary of "typedef'ed typename" -> "typename"
Definition: SgPyDataModel.h:196
SG::PyProxyMgr::m_clidMap
ClidMap_t m_clidMap
Definition: SgPyDataModel.h:206
SG::PyProxyMgr::pyclid
PyObject * pyclid(PyObject *tp)
returns a borrowed reference
Definition: SgPyDataModel.h:219
SG::PyProxyDict
a python front-end to the IProxyDict interface PyProxyDict encapsulates getting python objects from t...
Definition: SgPyDataModel.h:406
SG::PyProxyMgr::clid
CLID clid(PyObject *tp)
Definition: SgPyDataModel.h:274
BchCleanup.mgr
mgr
Definition: BchCleanup.py:294
python.PyAthena.module
module
Definition: PyAthena.py:131
python.utils.AtlRunQueryDQUtils.p
p
Definition: AtlRunQueryDQUtils.py:210
IDictLoaderSvc::load_type
virtual const RootType load_type(const std::string &type_name, bool recursive=false)=0
retrieve a RootType by name (auto)loading the dictionary by any necessary means.
python.trfUtils.call
def call(args, bufsize=0, executable=None, stdin=None, preexec_fn=None, close_fds=False, shell=False, cwd=None, env=None, universal_newlines=False, startupinfo=None, creationflags=0, message="", logger=msg, loglevel=None, timeout=None, retry=2, timefactor=1.5, sleeptime=10)
Definition: trfUtils.py:155
lumiFormat.i
int i
Definition: lumiFormat.py:85
Reflex::SCOPED
@ SCOPED
Definition: RootType.h:27
COOLRates.alias
alias
Definition: COOLRates.py:1172
Handler::svc
AthROOTErrorHandlerSvc * svc
Definition: AthROOTErrorHandlerSvc.cxx:10
CLID
uint32_t CLID
The Class ID type.
Definition: Event/xAOD/xAODCore/xAODCore/ClassID_traits.h:47
SG::PyProxyMgr::importDictAliases
PyObject * importDictAliases()
import the dictionary of aliases from a well known location
Definition: SgPyDataModel.h:369
TScopeAdapter::Name
std::string Name(unsigned int mod=Reflex::SCOPED) const
Definition: RootType.cxx:607
SG::PyProxyMgr::m_proxyMap
PyProxyMap_t m_proxyMap
Definition: SgPyDataModel.h:202
SG::PyProxyMgr::clid_from_tid
CLID clid_from_tid(PyObject *tp)
Definition: SgPyDataModel.h:306
SG::PyProxyMgr::m_clidSvc
IClassIDSvc * m_clidSvc
Definition: SgPyDataModel.h:194
SG::PyProxyMgr::m_clids
PyObject * m_clids
a dictionary of 'typename' -> CLID (and reverse CLID->'typename')
Definition: SgPyDataModel.h:199
SG::PyProxyMgr::PyProxyMgr
PyProxyMgr()
Definition: SgPyDataModel.cxx:165
id
SG::auxid_t id
Definition: Control/AthContainers/Root/debug.cxx:220
RootUtils::PyGetString
std::pair< std::string, bool > PyGetString(PyObject *s)
Convert python string -> C++ string for py2 and py3.
Definition: PyGetString.h:40
SG::PyProxyMgr::pytp
PyObject * pytp(PyObject *clid)
returns a borrowed reference
Definition: SgPyDataModel.h:238
PyObject
_object PyObject
Definition: IPyComponent.h:26
ServiceHandle< IClassIDSvc >