CMS 3D CMS Logo

 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Pages
FWItemAccessorFactory.cc
Go to the documentation of this file.
1 // -*- C++ -*-
2 //
3 // Package: Core
4 // Class : FWItemAccessorFactory
5 //
6 // Implementation:
7 // <Notes on implementation>
8 //
9 // Original Author: Chris Jones
10 // Created: Sat Oct 18 14:48:14 EDT 2008
11 // $Id: FWItemAccessorFactory.cc,v 1.12 2012/06/26 22:13:04 wmtan Exp $
12 //
13 
14 // system include files
15 #include <iostream>
16 #include "TClass.h"
17 #include "TVirtualCollectionProxy.h"
18 #include "Reflex/Type.h"
19 #include "Reflex/Member.h"
20 
21 // user include files
27 
28 //
29 // constants, enums and typedefs
30 //
31 
32 //
33 // static data member definitions
34 //
35 
36 //
37 // constructors and destructor
38 //
40 {
41 }
42 
43 // FWItemAccessorFactory::FWItemAccessorFactory(const FWItemAccessorFactory& rhs)
44 // {
45 // // do actual copying here;
46 // }
47 
49 {
50 }
51 
52 //
53 // assignment operators
54 //
55 // const FWItemAccessorFactory& FWItemAccessorFactory::operator=(const FWItemAccessorFactory& rhs)
56 // {
57 // //An exception safe implementation is
58 // FWItemAccessorFactory temp(rhs);
59 // swap(rhs);
60 //
61 // return *this;
62 // }
63 
64 //
65 // member functions
66 //
67 
68 //
69 // const member functions
70 //
71 
94 boost::shared_ptr<FWItemAccessorBase>
95 FWItemAccessorFactory::accessorFor(const TClass* iClass) const
96 {
97  static const bool debug = false;
98 
99  TClass *member = 0;
100  size_t offset=0;
101 
102  if(hasTVirtualCollectionProxy(iClass))
103  {
104  if (debug)
105  fwLog(fwlog::kDebug) << "class " << iClass->GetName()
106  << " uses FWItemTVirtualCollectionProxyAccessor." << std::endl;
107  return boost::shared_ptr<FWItemAccessorBase>(
109  boost::shared_ptr<TVirtualCollectionProxy>(iClass->GetCollectionProxy()->Generate())));
110  }
111  else if (hasMemberTVirtualCollectionProxy(iClass, member,offset))
112  {
113  if (debug)
114  fwLog(fwlog::kDebug) << "class "<< iClass->GetName()
115  << " only contains data member " << member->GetName()
116  << " which uses FWItemTVirtualCollectionProxyAccessor."
117  << std::endl;
118 
119  return boost::shared_ptr<FWItemAccessorBase>(
121  boost::shared_ptr<TVirtualCollectionProxy>(member->GetCollectionProxy()->Generate()),
122  offset));
123  }
124 
125  // Iterate on the available plugins and use the one which handles
126  // the iClass type.
127  // NOTE: This is done only a few times, not really performance critical.
128  // If you want this to be fast, the loop can be moved in the
129  // constructor. Notice that this will require constructing FWEventItemsManager
130  // after the plugin manager (i.e. invoking AutoLibraryLoader::enable()) is configured
131  // (i.e. invoking AutoLibraryLoader::enable()) in CmsShowMain.
132  std::string accessorName;
133  if (hasAccessor(iClass, accessorName))
134  {
135  if (debug)
136  fwLog(fwlog::kDebug) << "class " << iClass->GetName() << " uses "
137  << accessorName << "." << std::endl;
138  return boost::shared_ptr<FWItemAccessorBase>(FWItemAccessorRegistry::get()->create(accessorName, iClass));
139  }
140 
141  return boost::shared_ptr<FWItemAccessorBase>(new FWItemSingleAccessor(iClass));
142 }
143 
147 bool
149 {
150  // Check if this is a collection known by ROOT but also that the item held by
151  // the colletion actually has a dictionary
152  return iClass &&
153  iClass->GetCollectionProxy() &&
154  iClass->GetCollectionProxy()->GetValueClass() &&
155  iClass->GetCollectionProxy()->GetValueClass()->IsLoaded();
156 }
157 
169 bool
171  TClass *&oMember,
172  size_t& oOffset)
173 {
174  assert(iClass->GetTypeInfo());
175  Reflex::Type dataType(Reflex::Type::ByTypeInfo(*(iClass->GetTypeInfo())));
176  assert(dataType != Reflex::Type());
177 
178  // If the object has more than one data member, we avoid guessing.
179  if (dataType.DataMemberSize() != 1)
180  return false;
181 
182  Reflex::Type memType(dataType.DataMemberAt(0).TypeOf());
183  assert(memType != Reflex::Type());
184  //make sure this is the real type and not a typedef
185  memType = memType.FinalType();
186  oMember = TClass::GetClass(memType.TypeInfo());
187  oOffset = dataType.DataMemberAt(0).Offset();
188 
189  // Check if this is a collection known by ROOT but also that the item held by
190  // the colletion actually has a dictionary
191 
192  if (!hasTVirtualCollectionProxy(oMember))
193  return false;
194 
195  return true;
196 }
197 
205 bool
206 FWItemAccessorFactory::hasAccessor(const TClass *iClass, std::string &result)
207 {
208  const std::vector<edmplugin::PluginInfo> &available
209  = FWItemAccessorRegistry::get()->available();
210 
211  for (size_t i = 0, e = available.size(); i != e; ++i)
212  {
213  std::string name = available[i].name_;
214  std::string type = name.substr(0, name.find_first_of('@'));
215  if (iClass->GetTypeInfo()->name() == type)
216  {
217  result.swap(name);
218  return true;
219  }
220  }
221  return false;
222 }
223 
230 {
231  std::string accessorName;
232  TClass *member = 0;
233  size_t offset=0;
234 
235  // This is pretty much the same thing that happens
238  || FWItemAccessorFactory::hasAccessor(iClass, accessorName));
239 }
240 
241 //
242 // static member functions
243 //
type
Definition: HCALResponse.h:22
int i
Definition: DBlmapReader.cc:9
static bool classAccessedAsCollection(const TClass *)
tuple result
Definition: query.py:137
unsigned int offset(bool)
#define fwLog(_level_)
Definition: fwLog.h:51
static bool hasTVirtualCollectionProxy(const TClass *iClass)
static bool hasMemberTVirtualCollectionProxy(const TClass *iClass, TClass *&oMember, size_t &oOffset)
static bool hasAccessor(const TClass *iClass, std::string &result)
#define debug
Definition: MEtoEDMFormat.h:34
boost::shared_ptr< FWItemAccessorBase > accessorFor(const TClass *) const
T get(const Candidate &c)
Definition: component.h:56