Commits

Anonymous committed 847ec8e

first implementation of AthenaInternal::thinContainer

  • Participants
  • Parent commits 0e24913

Comments (0)

Files changed (4)

+2008-01-15  Sebastien Binet  <binet@lblbox>
+
+	* tagging StoreGateBindings-00-00-03
+	* first implementation of AthenaInternal::thinContainer
+	  need to pour more work into PyThinningHdlr 
+	  (require sthg like Scott's DVCollectionProxy)
+	* M StoreGateBindings/selection.xml
+	* M src/StoreGateBindingsDict.h
+	* M src/StoreGatePyExt.cxx
+
 2007-12-18  Sebastien Binet  <binet@lblbox>
 
 	* tagging StoreGateBindings-00-00-02

File StoreGateBindings/selection.xml

    <namespace name="AthenaInternal"/>
    <function name="AthenaInternal::retrieveObjectFromStore"/>
    <function name="AthenaInternal::recordObjectToStore"/>
+   <function name="AthenaInternal::thinContainer" />
+
 </lcgdict>

File src/StoreGateBindingsDict.h

 
 #include "StoreGate/StoreGateSvc.h"
 #include "StoreGate/StoreGate.h"
+#include "AthenaKernel/IThinningSvc.h"
 
 struct _object;
 typedef _object PyObject;
 
 namespace AthenaInternal {
 
-   PyObject* retrieveObjectFromStore( StoreGateSvc*, 
-				      PyObject* tp, PyObject* key, void*& res );
+  PyObject* retrieveObjectFromStore( StoreGateSvc*, 
+				     PyObject* tp, PyObject* key, void*& res );
 
-   PyObject* recordObjectToStore( StoreGateSvc*, 
-				  PyObject* obj, PyObject* key );
+  PyObject* recordObjectToStore( StoreGateSvc*, 
+				 PyObject* obj, PyObject* key );
 
+  PyObject* thinContainer( IThinningSvc*,
+			   PyObject* container,
+			   PyObject* filter,
+			   int op );
 }
 
 #endif // not STOREGATEBINDINGS_STOREGATEBINDINGSDICT_H 

File src/StoreGatePyExt.cxx

+///////////////////////// -*- C++ -*- /////////////////////////////
 // Hide this #include from checkreq so that it doesn't keep giving us warnings.
 #define PYTHON_INC "Python.h"
 #include PYTHON_INC
 #include "GaudiKernel/Bootstrap.h"
 #include "GaudiKernel/DataObject.h"
 #include "AthenaKernel/IClassIDSvc.h"
+#include "AthenaKernel/IThinningSvc.h"
 
 // Reflex includes
 #include "Reflex/Type.h"
     /// Access (and initialize) the pointer to the @c IClassIDSvc
     static IClassIDSvc* clidSvc();
   };
-}
 
-PyObject* AthenaInternal::retrieveObjectFromStore(
-      StoreGateSvc* store, PyObject* tp, PyObject* key, void*& res )
+  /**
+   * @brief Concrete @c IThinningHdlr to handle the thinning of an object via 
+   *        its python binding and use the Root dictionary to do conversions.
+   */
+  struct PyThinningHdlr : ::IThinningHdlr
+  {
+  
+    /** @brief Constructor to handle thinning of a python object
+     */
+    PyThinningHdlr( PyROOT::ObjectProxy* obj );
+
+    /** @brief remove an element from the proxied @c DataVector
+     */
+    virtual void remove( const std::size_t idx );
+    /** @brief pack the proxied @c DataVector
+     *         This is needed in order to keep element link indices consistent
+     *         and T/P converters unchanged.
+     */
+    virtual void pack();
+  
+    /** @brief unpack the proxied @c DataVector ie: restore it as it was 
+     *         *before* any thinning took place
+     */
+    virtual void unpack();
+  private:
+    /// Pointer to the held pyroot object.
+    PyROOT::ObjectProxy* m_container;
+  };
+} //> end namespace SG
+
+PyObject* 
+AthenaInternal::retrieveObjectFromStore( StoreGateSvc* store, 
+					 PyObject* tp, PyObject* key, 
+					 void*& res )
 {
    static IClassIDSvc* s_clidsvc = 0;
 
   
   std::string name = PyString_AS_STRING( pyname );
   CLID id = CLID_NULL;
-  StatusCode sc = s_clidsvc->getIDOfTypeName( name, id );
-  if ( sc.isFailure() ) {
+  if ( s_clidsvc->getIDOfTypeName( name, id ).isFailure() ) {
     PyErr_Format( PyExc_NameError, "ID of %s is unknown", name.c_str() );
     return 0;
   }
   PyROOT::ObjectProxy* pyRootObj = (PyROOT::ObjectProxy*)obj;
   DataObject* dataObj = new SG::PyDataBucket( pyRootObj, id );
   static bool allowMods = true;
-  if ( !store->typeless_record( dataObj, PyString_AS_STRING(key),
-				pyRootObj->GetObject(),
-				allowMods ).isSuccess() ) {
-      PyErr_SetString( PyExc_RuntimeError, "Failed to record py-dataobject" );
+  int sc = store->typeless_record( dataObj, PyString_AS_STRING(key),
+				   pyRootObj->GetObject(),
+				   allowMods ).isSuccess()
+    ? 1
+    : 0; 
+  return Py_BuildValue( const_cast<char*>("i"), sc );
+}
+
+PyObject* 
+AthenaInternal::thinContainer( IThinningSvc* self,
+			       PyObject* container_,
+			       PyObject* filter_,
+			       int op )
+{
+// unlikely to happen, but checking is cheap
+   if ( ! self ) {
+      PyErr_SetString( PyExc_RuntimeError, 
+		       "no thinning svc available, is Athena initialized?" );
       return 0;
-  }
+   }
 
-  Py_INCREF( Py_None );
-  return Py_None;
+   PyROOT::ObjectProxy* container = (PyROOT::ObjectProxy*)container_;
+   typedef IThinningSvc::Filter_t Filter_t;
+   // FIXME: won't work b/c of damn specialization of std::vector<bool> !!
+   // -> change IThinningSvc::filter interface or,
+   // -> copy the python array of booleans into a temporary vector<bool>
+   Filter_t& filter = 
+     *(Filter_t*)(((PyROOT::ObjectProxy*)filter_)->GetObject());
+
+   SG::DataProxy* proxy = self->deep_proxy( container->GetObject() );
+   if ( !proxy ) {
+     return 0;
+   }
+
+   IThinningHdlr* hdlr = self->handler(proxy);
+   if ( 0 == hdlr ) {
+     hdlr = new SG::PyThinningHdlr( container );
+   }
+
+//    const IThinningSvc::Operator::Type op = op_ == 0 
+//      ? IThinningSvc::Operator::
+   int sc = self->filter_impl( hdlr, proxy, filter, 
+			       (IThinningSvc::Operator::Type)op ).isSuccess()
+	      ? 1
+	      : 0; 
+   return Py_BuildValue( const_cast<char*>("i"), sc );
 }
 
 //
     std::abort();
     return 0;
 //     new SG::PyDataBucket( m_type, copy<>(m_pyObj), m_clid );
-   }
+  }
+
+  /////////////////////////////////////////////////////////////////////////////
+  // PyThinningHdlr implementation
+
+  PyThinningHdlr::PyThinningHdlr( PyROOT::ObjectProxy* obj ) :
+    IThinningHdlr(     ),
+    m_container  ( obj )
+  {}
+
+  /** @brief remove an element from the proxied @c DataVector
+   */
+  void PyThinningHdlr::remove( const std::size_t /*idx*/ )
+  {}
+  
+  /** @brief pack the proxied @c DataVector
+   *         This is needed in order to keep element link indices consistent
+   *         and T/P converters unchanged.
+   */
+  void PyThinningHdlr::pack()
+  {}
+  
+  /** @brief unpack the proxied @c DataVector ie: restore it as it was 
+   *         *before* any thinning took place
+   */
+  void PyThinningHdlr::unpack()
+  {}
 
 } //< end namespace SG