[odb-users] Global Custom Session in Multi-Threading Application

韩彬 seu.hanbin at gmail.com
Wed Jun 10 09:30:19 EDT 2020


We are building our application based on odb-2.4.0  and PostgreSQL
(with ibodb-pgsql-2.4.0),
and we are trying to implement a *global* *thread-safe custom session
rather than the default thread-local-session* in our application according
to ODB manual 11.2
<https://www.codesynthesis.com/products/odb/doc/manual.xhtml#11.2> and
the custom
session example
in odb-tests.

Basically our custom session uses a thread-safe tbb::cocurrent_hash_map as
object map like this,

>   template <typename T>
>   struct object_map: object_map_base,
>                      tbb::cocurrent_hash_map<typename odb::object_traits<T>::id_type,
>                               object_data<T> >
>   { };
And I also add a global mutex on each access operation to the custom
session, like this. So the access to our custom session and object map are
guarantee to be thread-safe.

> static std::mutex _mtx;

_cache_insert (){

    std::lock_guard  _lock(_mtx);



_cache_find () {

       std::lock_guard _lock((_mtx) ;



_cache_erase ()
> {

     std::lock_guard _lock(_mtx);



In our application, we have only *one global session *and *multiple
threads. *In each thread , we have *one transaction *to* load DATA *
from PostgreSQL.
Those *DATA* *may have a shared_ptr point to the same object.  But we found
that sometimes the shared_ptr will be initialized with some weird number
instead of the real obj in db. *
*db pragma ...*
*struct DATA{*
*   //...*
*   std::shared_ptr<T> obj;*

*class Application{*
*    session s;*
*    void parallel_update_db() {*

*        tbb::parallel_for(*
*             //....*
*             transaction t;*
*             // load DATA*
*        );*

*    }*

We noticed that after ODB calls the* _cache_insert *operation in our
session, *the inserted object is still not initialized with the real data
in db, and according to line 89 in *the load method in libodb-pgsql
actually the inserted object will actually be initialized after the
_cache_insert operation.  So given that we have two threads load and insert
the same object to our object map, would one thread end up with an invalid
object pointer?  Or are there any possible issue with my implementation and
usage of custom session?*

More information about the odb-users mailing list