1 // Copyright (C) 2007-2016 CEA/DEN, EDF R&D, OPEN CASCADE
3 // This library is free software; you can redistribute it and/or
4 // modify it under the terms of the GNU Lesser General Public
5 // License as published by the Free Software Foundation; either
6 // version 2.1 of the License, or (at your option) any later version.
8 // This library is distributed in the hope that it will be useful,
9 // but WITHOUT ANY WARRANTY; without even the implied warranty of
10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11 // Lesser General Public License for more details.
13 // You should have received a copy of the GNU Lesser General Public
14 // License along with this library; if not, write to the Free Software
15 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
19 // Author : Anthony GEAY (EDF R&D)
21 #include "SALOMESDS_DataScopeServer.hxx"
22 #include "SALOMESDS_DataServerManager.hxx"
23 #include "SALOMESDS_PickelizedPyObjRdOnlyServer.hxx"
24 #include "SALOMESDS_PickelizedPyObjRdExtServer.hxx"
25 #include "SALOMESDS_PickelizedPyObjRdWrServer.hxx"
26 #include "SALOMESDS_PickelizedPyObjRdExtInitServer.hxx"
27 #include "SALOMESDS_TrustTransaction.hxx"
28 #include "SALOMESDS_KeyWaiter.hxx"
29 #include "SALOMESDS_Transaction.hxx"
30 #include "SALOME_NamingService.hxx"
31 #include "SALOMESDS_Exception.hxx"
37 // agy : awful, to be factorized with ContainerManager.
42 #define getpid _getpid
45 using namespace SALOMESDS;
47 std::size_t DataScopeServerBase::COUNTER=0;
49 #if PY_VERSION_HEX < 0x03050000
51 Py_EncodeLocale(const wchar_t *arg, size_t *size)
53 return _Py_wchar2char(arg, size);
56 Py_DecodeLocale(const char *arg, size_t *size)
58 return _Py_char2wchar(arg, size);
62 void DataScopeKiller::shutdown()
68 RequestSwitcher::RequestSwitcher(CORBA::ORB_ptr orb, DataScopeServerTransaction *ds):RequestSwitcherBase(orb),_ds(ds)
72 SALOME::StringVec *RequestSwitcher::listVars()
74 return _ds->listVars();
77 SALOME::ByteVec *RequestSwitcher::fetchSerializedContent(const char *varName)
79 return _ds->fetchSerializedContent(varName);
82 void RequestSwitcher::fetchAndGetAccessOfVar(const char *varName, CORBA::String_out access, SALOME::ByteVec_out data)
84 return _ds->fetchAndGetAccessOfVar(varName,access,data);
87 DataScopeServerBase::DataScopeServerBase(CORBA::ORB_ptr orb, SALOME::DataScopeKiller_var killer, const std::string& scopeName):_globals(0),_locals(0),_pickler(0),_orb(CORBA::ORB::_duplicate(orb)),_name(scopeName),_killer(killer)
91 DataScopeServerBase::DataScopeServerBase(const DataScopeServerBase& other):omniServant(other),ServantBase(other),_globals(0),_locals(0),_pickler(0),_name(other._name),_vars(other._vars),_killer(other._killer)
95 DataScopeServerBase::~DataScopeServerBase()
97 // _globals is borrowed ref -> do nothing
100 for(std::list< std::pair< SALOME::BasicDataServer_var, BasicDataServer * > >::const_iterator it=_vars.begin();it!=_vars.end();it++)
102 BasicDataServer *obj((*it).second);
111 * Called remotely -> to protect against throw
113 void DataScopeServerBase::ping()
118 * Called remotely -> to protect against throw
120 char *DataScopeServerBase::getScopeName()
122 return CORBA::string_dup(_name.c_str());
126 * Called remotely -> to protect against throw
128 SALOME::StringVec *DataScopeServerBase::listVars()
130 SALOME::StringVec *ret(new SALOME::StringVec);
131 std::size_t sz(_vars.size());
133 std::list< std::pair< SALOME::BasicDataServer_var, BasicDataServer * > >::iterator it(_vars.begin());
134 for(std::size_t i=0;i<sz;it++,i++)
136 BasicDataServer *obj((*it).second);
137 std::string name(obj->getVarNameCpp());
138 (*ret)[i]=CORBA::string_dup(name.c_str());
143 CORBA::Boolean DataScopeServerBase::existVar(const char *varName)
145 std::list< std::pair< SALOME::BasicDataServer_var, BasicDataServer * > >::const_iterator it(_vars.begin());
146 for(;it!=_vars.end();it++)
147 if((*it).second->getVarNameCpp()==varName)
152 SALOME::BasicDataServer_ptr DataScopeServerBase::retrieveVarInternal(const char *varName)
154 std::list< std::pair< SALOME::BasicDataServer_var, BasicDataServer * > >::const_iterator it0(retrieveVarInternal3(varName));
155 return SALOME::BasicDataServer::_duplicate((*it0).first);
158 BasicDataServer *DataScopeServerBase::retrieveVarInternal2(const std::string& varName)
160 std::list< std::pair< SALOME::BasicDataServer_var, BasicDataServer * > >::const_iterator it0(retrieveVarInternal3(varName));
161 return (*it0).second;
164 void DataScopeServerBase::deleteVar(const char *varName)
166 std::string varNameCpp(varName);
167 std::vector<std::string> allNames(getAllVarNames());
168 std::vector<std::string>::iterator it(std::find(allNames.begin(),allNames.end(),varNameCpp));
169 if(it==allNames.end())
171 std::ostringstream oss; oss << "DataScopeServerBase::deleteVar : name \"" << varNameCpp << "\" does not exists ! Possibilities are :";
172 std::copy(allNames.begin(),allNames.end(),std::ostream_iterator<std::string>(oss,", "));
173 throw Exception(oss.str());
175 std::size_t pos(std::distance(allNames.begin(),it));
176 std::list< std::pair< SALOME::BasicDataServer_var, BasicDataServer * > >::iterator it0(_vars.begin());
177 for(std::size_t ii=0;ii<pos;ii++,it0++);
178 (*it0).second->decrRef();
182 CORBA::Boolean DataScopeServerBase::shutdownIfNotHostedByDSM(SALOME::DataScopeKiller_out killer)
184 SALOME_NamingService ns(_orb);
185 CORBA::Object_var obj(ns.Resolve(DataServerManager::NAME_IN_NS));
186 SALOME::DataServerManager_var dsm(SALOME::DataServerManager::_narrow(obj));
187 if(CORBA::is_nil(dsm))
188 throw Exception("Unable to reach in the NS the unique DataServerManager instance of the Session !");
189 // destroy ref in the naming service
190 std::string fullScopeName(SALOMESDS::DataServerManager::CreateAbsNameInNSFromScopeName(_name));
191 ns.Destroy_Name(fullScopeName.c_str());
192 // establish if dsm and this shared the same POA. If yes dsm and this are collocated !
193 PortableServer::ServantBase *ret(0);
196 ret=_poa->reference_to_servant(dsm);
198 catch(...) { ret=0; }
203 killer=SALOME::DataScopeKiller::_duplicate(_killer);
210 killer=SALOME::DataScopeKiller::_duplicate(_killer);
215 SALOME::ByteVec *DataScopeServerBase::fetchSerializedContent(const char *varName)
217 BasicDataServer *var(retrieveVarInternal2(varName));
218 PickelizedPyObjServer *varc(dynamic_cast<PickelizedPyObjServer *>(var));
221 std::ostringstream oss; oss << "DataScopeServerBase::fetchSerializedContent : var \"" << varName << "\" exists but it is not serialized !";
222 throw Exception(oss.str());
224 return varc->fetchSerializedContent();
227 SALOME::SeqOfByteVec *DataScopeServerBase::getAllKeysOfVarWithTypeDict(const char *varName)
229 BasicDataServer *var(retrieveVarInternal2(varName));
230 PickelizedPyObjServer *varc(dynamic_cast<PickelizedPyObjServer *>(var));
233 std::ostringstream oss; oss << "DataScopeServerBase::getAllKeysOfVarWithTypeDict : var \"" << varName << "\" exists but it is not serialized !";
234 throw Exception(oss.str());
238 std::ostringstream oss; oss << "DataScopeServerBase::getAllKeysOfVarWithTypeDict : var \"" << varName << "\" exists but it is not a PyDict !";
239 throw Exception(oss.str());
241 PyObject *keys(PyDict_Keys(varc->getPyObj()));
242 if(!PyList_Check(keys))
244 std::ostringstream oss; oss << "DataScopeServerBase::getAllKeysOfVarWithTypeDict : var \"" << varName << "\" has keys but not of type list !";
245 throw Exception(oss.str());
247 Py_ssize_t sz(PyList_Size(keys));
248 SALOME::SeqOfByteVec *ret(new SALOME::SeqOfByteVec);
250 for(Py_ssize_t i=0;i<sz;i++)
252 PyObject *item(PyList_GetItem(keys,i));
254 std::string pickel(varc->pickelize(item));//item consumed
255 PickelizedPyObjServer::FromCppToByteSeq(pickel,(*ret)[i]);
261 void DataScopeServerBase::takeANap(CORBA::Double napDurationInSec)
263 if(napDurationInSec<0.)
264 throw Exception("DataScopeServerBase::takeANap : negative value !");
266 struct timespec req,rem;
267 long nbSec((long)napDurationInSec);
268 double remainTime(napDurationInSec-(double)nbSec);
270 req.tv_nsec=(long)(remainTime*1000000.);
271 int ret(nanosleep(&req,&rem));
273 throw Exception("DataScopeServerBase::takeANap : nap not finished as expected !");
275 throw Exception("DataScopeServerBase::takeANap : not implemented for Windows !");
279 void DataScopeServerBase::initializePython(int argc, char *argv[])
282 PyEval_InitThreads();
283 wchar_t **changed_argv = new wchar_t*[argc]; // Setting arguments
284 for (int i = 0; i < argc; i++)
285 changed_argv[i] = Py_DecodeLocale(argv[i], NULL);
286 PySys_SetArgv(argc, changed_argv);
287 PyObject *mainmod(PyImport_AddModule("__main__"));
288 _globals=PyModule_GetDict(mainmod);
289 if(PyDict_GetItemString(_globals, "__builtins__") == NULL)
291 PyObject *bimod(PyImport_ImportModule("__builtin__"));
292 if (bimod == NULL || PyDict_SetItemString(_globals, "__builtins__", bimod) != 0)
293 Py_FatalError("can't add __builtins__ to __main__");
296 _locals=PyDict_New();
297 PyObject *tmp(PyList_New(0));
298 _pickler=PyImport_ImportModuleLevel(const_cast<char *>("pickle"),_globals,_locals,tmp,0);
301 void DataScopeServerBase::registerToSalomePiDict() const
303 PyObject *mod(PyImport_ImportModule("addToKillList"));//new value
306 PyObject *meth(PyObject_GetAttrString(mod,"addToKillList"));//new value
308 { Py_XDECREF(mod); return ; }
309 PyObject *args(PyTuple_New(2));
310 PyTuple_SetItem(args,0,PyLong_FromLong(getpid()));
311 PyTuple_SetItem(args,1,PyUnicode_FromString("SALOME_DataScopeServerBase"));
312 PyObject *res(PyObject_CallObject(meth,args));
319 void DataScopeServerBase::setPOA(PortableServer::POA_var poa)
324 void DataScopeServerBase::registerInNS(SALOME::DataScopeServerBase_ptr ptr)
326 std::string fullScopeName(SALOMESDS::DataServerManager::CreateAbsNameInNSFromScopeName(_name));
327 SALOME_NamingService ns(_orb);
328 ns.Register(ptr,fullScopeName.c_str());
331 std::string DataScopeServerBase::BuildTmpVarNameFrom(const std::string& varName)
333 std::ostringstream oss;
334 oss << varName << "@" << COUNTER++;
338 std::vector< std::string > DataScopeServerBase::getAllVarNames() const
340 std::size_t sz(_vars.size());
341 std::vector<std::string> ret(sz);
342 std::list< std::pair< SALOME::BasicDataServer_var, BasicDataServer * > >::const_iterator it(_vars.begin());
343 for(std::size_t i=0;i<sz;it++,i++)
344 ret[i]=(*it).second->getVarNameCpp();
348 bool DataScopeServerBase::isExistingVar(const std::string& varName) const
350 std::vector<std::string> allNames(getAllVarNames());
351 std::vector<std::string>::iterator it(std::find(allNames.begin(),allNames.end(),varName));
352 return it!=allNames.end();
355 void DataScopeServerBase::checkNotAlreadyExistingVar(const std::string& varName) const
357 if(isExistingVar(varName))
359 std::ostringstream oss; oss << "DataScopeServerBase::checkNotAlreadyExistingVar : name \"" << varName << "\" already exists !";
360 throw Exception(oss.str());
364 void DataScopeServerBase::checkExistingVar(const std::string& varName) const
366 std::vector<std::string> allNames(getAllVarNames());
367 std::vector<std::string>::iterator it(std::find(allNames.begin(),allNames.end(),varName));
368 if(it==allNames.end())
370 std::ostringstream oss; oss << "DataScopeServerBase::checkExistingVar : name \"" << varName << "\" does not exist !";
371 throw Exception(oss.str());
375 PickelizedPyObjServer *DataScopeServerBase::checkVarExistingAndDict(const std::string& varName)
377 checkExistingVar(varName);
378 BasicDataServer *var(retrieveVarInternal2(varName.c_str()));
379 PickelizedPyObjServer *ret(dynamic_cast<PickelizedPyObjServer *>(var));
382 std::ostringstream oss; oss << "TransactionAddKeyValueHard::prepareRollBackInCaseOfFailure : var \"" << varName << "\"exists but it is not serialized !";
383 throw Exception(oss.str());
387 std::ostringstream oss; oss << "TransactionAddKeyValueHard::prepareRollBackInCaseOfFailure : var \"" << varName << "\"exists but it is not a Dict !";
388 throw Exception(oss.str());
393 void DataScopeServerBase::moveStatusOfVarFromRdWrToRdOnly(const std::string& varName)
395 std::list< std::pair< SALOME::BasicDataServer_var, BasicDataServer * > >::iterator it(retrieveVarInternal4(varName));
396 std::pair< SALOME::BasicDataServer_var, BasicDataServer * >& p(*it);
397 PickelizedPyObjRdWrServer *varc(dynamic_cast<PickelizedPyObjRdWrServer *>(p.second));
399 throw Exception("DataScopeServerBase::moveStatusOfVarFromRdWrToRdOnly : var is not a RdWr !");
400 PyObject *pyobj(varc->getPyObj()); Py_XINCREF(pyobj);
401 PickelizedPyObjRdOnlyServer *newVar(new PickelizedPyObjRdOnlyServer(this,varName,pyobj));
402 CORBA::Object_var obj(newVar->activate());
403 SALOME::BasicDataServer_var obj2(SALOME::BasicDataServer::_narrow(obj));
404 p.first=obj2; p.second=newVar;
408 void DataScopeServerBase::moveStatusOfVarFromRdOnlyToRdWr(const std::string& varName)
410 std::list< std::pair< SALOME::BasicDataServer_var, BasicDataServer * > >::iterator it(retrieveVarInternal4(varName));
411 std::pair< SALOME::BasicDataServer_var, BasicDataServer * >& p(*it);
412 PickelizedPyObjRdOnlyServer *varc(dynamic_cast<PickelizedPyObjRdOnlyServer *>(p.second));
414 throw Exception("DataScopeServerBase::moveStatusOfVarFromRdOnlyToRdWr : var is not a RdWr !");
415 PyObject *pyobj(varc->getPyObj()); Py_XINCREF(pyobj);
416 PickelizedPyObjRdWrServer *newVar(new PickelizedPyObjRdWrServer(this,varName,pyobj));
417 CORBA::Object_var obj(newVar->activate());
418 SALOME::BasicDataServer_var obj2(SALOME::BasicDataServer::_narrow(obj));
419 p.first=obj2; p.second=newVar;
423 void DataScopeServerBase::moveStatusOfVarFromRdExtOrRdExtInitToRdExtInit(const std::string& varName)
425 std::list< std::pair< SALOME::BasicDataServer_var, BasicDataServer * > >::iterator it(retrieveVarInternal4(varName));
426 std::pair< SALOME::BasicDataServer_var, BasicDataServer * >& p(*it);
427 PickelizedPyObjRdExtServer *varc0(dynamic_cast<PickelizedPyObjRdExtServer *>(p.second));
428 PickelizedPyObjRdExtInitServer *varc1(dynamic_cast<PickelizedPyObjRdExtInitServer *>(p.second));
430 throw Exception("DataScopeServerBase::moveStatusOfVarFromRdExtOrRdExtInitToRdExtInit : var is neither RdExt nor RdExtInit !");
433 PickelizedPyObjRdExtInitServer *newVar(varc0->buildInitInstanceFrom(varName));
434 newVar->incrNbClients();
435 CORBA::Object_var obj(newVar->activate());
436 SALOME::BasicDataServer_var obj2(SALOME::BasicDataServer::_narrow(obj));
437 p.first=obj2; p.second=newVar;
441 varc1->incrNbClients();
444 void DataScopeServerBase::moveStatusOfVarFromRdExtOrRdExtInitToRdExt(const std::string& varName)
446 std::list< std::pair< SALOME::BasicDataServer_var, BasicDataServer * > >::iterator it(retrieveVarInternal4(varName));
447 std::pair< SALOME::BasicDataServer_var, BasicDataServer * >& p(*it);
448 PickelizedPyObjRdExtInitServer *varc0(dynamic_cast<PickelizedPyObjRdExtInitServer *>(p.second));
449 PickelizedPyObjRdExtServer *varc1(dynamic_cast<PickelizedPyObjRdExtServer *>(p.second));
451 throw Exception("DataScopeServerBase::moveStatusOfVarFromRdExtOrRdExtInitToRdExt : var is not a RdExtInit !");
454 if(varc0->decrNbClients())
456 PickelizedPyObjRdExtServer *newVar(varc0->buildStdInstanceFrom(varName));
457 CORBA::Object_var obj(newVar->activate());
458 SALOME::BasicDataServer_var obj2(SALOME::BasicDataServer::_narrow(obj));
459 p.first=obj2; p.second=newVar;
465 std::list< std::pair< SALOME::BasicDataServer_var, BasicDataServer * > >::const_iterator DataScopeServerBase::retrieveVarInternal3(const std::string& varName) const
467 std::vector<std::string> allNames(getAllVarNames());
468 std::vector<std::string>::iterator it(std::find(allNames.begin(),allNames.end(),varName));
469 if(it==allNames.end())
471 std::ostringstream oss; oss << "DataScopeServerBase::retrieveVarInternal3 : name \"" << varName << "\" does not exists ! Possibilities are :";
472 std::copy(allNames.begin(),allNames.end(),std::ostream_iterator<std::string>(oss,", "));
473 throw Exception(oss.str());
475 std::size_t pos(std::distance(allNames.begin(),it));
476 std::list< std::pair< SALOME::BasicDataServer_var, BasicDataServer * > >::const_iterator it0(_vars.begin());
477 for(std::size_t i=0;i<pos;i++,it0++);
481 std::list< std::pair< SALOME::BasicDataServer_var, BasicDataServer * > >::iterator DataScopeServerBase::retrieveVarInternal4(const std::string& varName)
483 std::vector<std::string> allNames(getAllVarNames());
484 std::vector<std::string>::iterator it(std::find(allNames.begin(),allNames.end(),varName));
485 if(it==allNames.end())
487 std::ostringstream oss; oss << "DataScopeServerBase::retrieveVarInternal4 : name \"" << varName << "\" does not exists ! Possibilities are :";
488 std::copy(allNames.begin(),allNames.end(),std::ostream_iterator<std::string>(oss,", "));
489 throw Exception(oss.str());
491 std::size_t pos(std::distance(allNames.begin(),it));
492 std::list< std::pair< SALOME::BasicDataServer_var, BasicDataServer * > >::iterator it0(_vars.begin());
493 for(std::size_t i=0;i<pos;i++,it0++);
499 DataScopeServer::DataScopeServer(CORBA::ORB_ptr orb, SALOME::DataScopeKiller_var killer, const std::string& scopeName):DataScopeServerBase(orb,killer,scopeName)
503 DataScopeServer::DataScopeServer(const DataScopeServer& other):omniServant(other),ServantBase(other),DataScopeServerBase(other)
507 SALOME::PickelizedPyObjRdOnlyServer_ptr DataScopeServer::createRdOnlyVar(const char *varName, const SALOME::ByteVec& constValue)
509 std::string varNameCpp(varName);
510 checkNotAlreadyExistingVar(varNameCpp);
511 PickelizedPyObjRdOnlyServer *tmp(new PickelizedPyObjRdOnlyServer(this,varNameCpp,constValue));
512 CORBA::Object_var ret(tmp->activate());
513 std::pair< SALOME::BasicDataServer_var, BasicDataServer * > p(SALOME::BasicDataServer::_narrow(ret),tmp);
515 return SALOME::PickelizedPyObjRdOnlyServer::_narrow(ret);
518 SALOME::PickelizedPyObjRdExtServer_ptr DataScopeServer::createRdExtVar(const char *varName, const SALOME::ByteVec& constValue)
520 std::string varNameCpp(varName);
521 checkNotAlreadyExistingVar(varNameCpp);
522 PickelizedPyObjRdExtServer *tmp(new PickelizedPyObjRdExtServer(this,varNameCpp,constValue));
523 CORBA::Object_var ret(tmp->activate());
524 std::pair< SALOME::BasicDataServer_var, BasicDataServer * > p(SALOME::BasicDataServer::_narrow(ret),tmp);
526 return SALOME::PickelizedPyObjRdExtServer::_narrow(ret);
529 SALOME::PickelizedPyObjRdWrServer_ptr DataScopeServer::createRdWrVar(const char *typeName, const char *varName)
531 std::string varNameCpp(varName),typeNameCpp(typeName);
532 checkNotAlreadyExistingVar(varNameCpp);
533 PickelizedPyObjRdWrServer *tmp(new PickelizedPyObjRdWrServer(this,typeNameCpp,varNameCpp));
534 CORBA::Object_var ret(tmp->activate());
535 std::pair< SALOME::BasicDataServer_var, BasicDataServer * > p(SALOME::BasicDataServer::_narrow(ret),tmp);
537 return SALOME::PickelizedPyObjRdWrServer::_narrow(ret);
540 DataScopeServer::~DataScopeServer()
546 DataScopeServerTransaction::DataScopeServerTransaction(CORBA::ORB_ptr orb, SALOME::DataScopeKiller_var killer, const std::string& scopeName):DataScopeServerBase(orb,killer,scopeName)
548 CORBA::Object_var obj(_orb->resolve_initial_references("RootPOA"));
549 PortableServer::POA_var poa(PortableServer::POA::_narrow(obj));
551 PortableServer::POAManager_var mgr(poa->the_POAManager());
552 CORBA::PolicyList policies;
554 PortableServer::ThreadPolicy_var threadPol(poa->create_thread_policy(PortableServer::ORB_CTRL_MODEL));
555 policies[0]=PortableServer::ThreadPolicy::_duplicate(threadPol);
556 PortableServer::POA_var poa2(poa->create_POA("POAForWaiters",mgr,policies));
557 threadPol->destroy();
559 _poa_for_key_waiter=poa2;
562 DataScopeServerTransaction::DataScopeServerTransaction(const DataScopeServerTransaction& other):omniServant(other),ServantBase(other),DataScopeServerBase(other),_poa_for_key_waiter(other.getPOA4KeyWaiter())
566 char *DataScopeServerTransaction::getAccessOfVar(const char *varName)
568 std::string varNameCpp(varName);
569 checkExistingVar(varNameCpp);
570 BasicDataServer *var(retrieveVarInternal2(varName));
572 throw Exception("DataScopeServerTransaction::getAccessOfVar : variable is NULL !");
573 PickelizedPyObjServer *varc(dynamic_cast<PickelizedPyObjServer *>(var));
575 throw Exception("DataScopeServerTransaction::getAccessOfVar : variable is not of type PickelizedPyObjServer !");
576 std::string ret(varc->getAccessStr());
577 return CORBA::string_dup(ret.c_str());
581 * This method is here to retrieve atomically accessStr and picklization.
583 void DataScopeServerTransaction::fetchAndGetAccessOfVar(const char *varName, CORBA::String_out access, SALOME::ByteVec_out data)
585 access=getAccessOfVar(varName);
586 data=fetchSerializedContent(varName);
589 void DataScopeServerTransaction::createRdOnlyVarInternal(const std::string& varName, const SALOME::ByteVec& constValue)
591 checkNotAlreadyExistingVar(varName);
592 PickelizedPyObjRdOnlyServer *tmp(new PickelizedPyObjRdOnlyServer(this,varName,constValue));
593 CORBA::Object_var ret(tmp->activate());
594 std::pair< SALOME::BasicDataServer_var, BasicDataServer * > p(SALOME::BasicDataServer::_narrow(ret),tmp);
598 void DataScopeServerTransaction::createRdExtVarInternal(const std::string& varName, const SALOME::ByteVec& constValue)
600 checkNotAlreadyExistingVar(varName);
601 PickelizedPyObjRdExtServer *tmp(new PickelizedPyObjRdExtServer(this,varName,constValue));
602 CORBA::Object_var ret(tmp->activate());
603 std::pair< SALOME::BasicDataServer_var, BasicDataServer * > p(SALOME::BasicDataServer::_narrow(ret),tmp);
607 void DataScopeServerTransaction::createRdExtVarFreeStyleInternal(const std::string& varName, const SALOME::ByteVec& constValue, std::vector<unsigned char>&& sha1)
609 if(!isExistingVar(varName))
611 PickelizedPyObjRdExtFreeStyleServer *tmp(new PickelizedPyObjRdExtFreeStyleServer(this,varName,constValue,std::move(sha1)));
612 CORBA::Object_var ret(tmp->activate());
613 std::pair< SALOME::BasicDataServer_var, BasicDataServer * > p(SALOME::BasicDataServer::_narrow(ret),tmp);
618 BasicDataServer *ds(retrieveVarInternal2(varName));
621 std::ostringstream oss;
622 oss << "DataScopeServerTransaction::createRdExtVarFreeStyleInternal : internal error 1 for varname \"" << varName << "\"!";
623 throw Exception(oss.str());
625 Sha1Keeper *ds2(dynamic_cast<Sha1Keeper *>(ds));
628 std::ostringstream oss;
629 oss << "DataScopeServerTransaction::createRdExtVarFreeStyleInternal : varname \"" << varName << "\" already exists with a non RdExtFreeStyle type !";
630 throw Exception(oss.str());
632 ds2->checkSha1(varName,sha1);
636 void DataScopeServerTransaction::createRdExtInitVarInternal(const std::string& varName, const SALOME::ByteVec& constValue)
638 checkNotAlreadyExistingVar(varName);
639 PickelizedPyObjRdExtInitServer *tmp(new PickelizedPyObjRdExtInitServer(this,varName,constValue));
640 CORBA::Object_var ret(tmp->activate());
641 std::pair< SALOME::BasicDataServer_var, BasicDataServer * > p(SALOME::BasicDataServer::_narrow(ret),tmp);
645 void DataScopeServerTransaction::createRdWrVarInternal(const std::string& varName, const SALOME::ByteVec& constValue)
647 checkNotAlreadyExistingVar(varName);
648 PickelizedPyObjRdWrServer *tmp(new PickelizedPyObjRdWrServer(this,varName,constValue));
649 CORBA::Object_var ret(tmp->activate());
650 std::pair< SALOME::BasicDataServer_var, BasicDataServer * > p(SALOME::BasicDataServer::_narrow(ret),tmp);
654 SALOME::Transaction_ptr DataScopeServerTransaction::createRdOnlyVarTransac(const char *varName, const SALOME::ByteVec& constValue)
656 checkNotAlreadyExistingVar(varName);
657 TransactionRdOnlyVarCreate *ret(new TransactionRdOnlyVarCreate(this,varName,constValue));
658 CORBA::Object_var obj(ret->activate());
659 return SALOME::Transaction::_narrow(obj);
662 SALOME::Transaction_ptr DataScopeServerTransaction::createRdExtVarTransac(const char *varName, const SALOME::ByteVec& constValue)
664 checkNotAlreadyExistingVar(varName);
665 TransactionRdExtVarCreate *ret(new TransactionRdExtVarCreate(this,varName,constValue));
666 CORBA::Object_var obj(ret->activate());
667 return SALOME::Transaction::_narrow(obj);
670 SALOME::Transaction_ptr DataScopeServerTransaction::createRdExtVarFreeStyleTransac(const char *varName, const SALOME::ByteVec& constValue, const SALOME::ByteVec& sha1)
671 {// no check on varName done here. Will be done on perform
672 TransactionRdExtVarFreeStyleCreate *ret(new TransactionRdExtVarFreeStyleCreate(this,varName,constValue,sha1));
673 CORBA::Object_var obj(ret->activate());
674 return SALOME::Transaction::_narrow(obj);
677 SALOME::Transaction_ptr DataScopeServerTransaction::createRdExtInitVarTransac(const char *varName, const SALOME::ByteVec& constValue)
679 checkNotAlreadyExistingVar(varName);
680 TransactionRdExtInitVarCreate *ret(new TransactionRdExtInitVarCreate(this,varName,constValue));
681 CORBA::Object_var obj(ret->activate());
682 return SALOME::Transaction::_narrow(obj);
685 SALOME::Transaction_ptr DataScopeServerTransaction::createRdWrVarTransac(const char *varName, const SALOME::ByteVec& constValue)
687 checkNotAlreadyExistingVar(varName);
688 TransactionRdWrVarCreate *ret(new TransactionRdWrVarCreate(this,varName,constValue));
689 CORBA::Object_var obj(ret->activate());
690 return SALOME::Transaction::_narrow(obj);
693 void DataScopeServerTransaction::addWaitKey(KeyWaiter *kw)
696 throw Exception("DataScopeServerTransaction::addWaitKey : NULL input object !");
697 _waiting_keys.push_back(kw);
700 void DataScopeServerTransaction::pingKey(PyObject *keyObj)
703 // this part does nothing except to be sure that in notify key all will be OK.
704 PyObject *args(PyTuple_New(1));
705 PyTuple_SetItem(args,0,keyObj); Py_XINCREF(keyObj);
706 for(std::list< KeyWaiter *>::iterator it=_waiting_keys.begin();it!=_waiting_keys.end();it++,ii++)
708 PyObject *waitKey((*it)->getKeyPyObj());
709 PyObject *meth(PyObject_GetAttrString(waitKey,"__eq__"));
712 std::ostringstream oss; oss << "DataScopeServerTransaction::pingKey : for object id #" << ii << " no __eq__ in pyobj !";
713 throw Exception(oss.str());
715 PyObject *res(PyObject_CallObject(meth,args));
719 std::ostringstream oss; oss << "DataScopeServerTransaction::pingKey : for object id #" << ii << " error during cmp(k,wk[i]) !";
720 throw Exception(oss.str());
725 std::ostringstream oss; oss << "DataScopeServerTransaction::pingKey : for object id #" << ii << " error during interpretation of cmp(k,wk[i]) !";
726 throw Exception(oss.str());
733 void DataScopeServerTransaction::notifyKey(const std::string& varName, PyObject *keyObj, PyObject *valueObj)
736 PyObject *args(PyTuple_New(1));
737 PyTuple_SetItem(args,0,keyObj); Py_XINCREF(keyObj);
738 std::list< KeyWaiter *> newList,listOfEltToWakeUp;
739 for(std::list< KeyWaiter *>::iterator it=_waiting_keys.begin();it!=_waiting_keys.end();it++,ii++)
741 if((*it)->getVarName()!=varName)
743 newList.push_back(*it);
746 PyObject *waitKey((*it)->getKeyPyObj());
747 PyObject *meth(PyObject_GetAttrString(waitKey,"__eq__"));
750 std::ostringstream oss; oss << "DataScopeServerTransaction::pingKey : for object id #" << ii << " no __eq__ in pyobj !";
751 throw Exception(oss.str());
753 PyObject *res(PyObject_CallObject(meth,args));
755 if(!PyBool_Check(res))
757 std::ostringstream oss; oss << "DataScopeServerTransaction::pingKey : for object id #" << ii << " no __eq__ in pyobj !";
758 throw Exception(oss.str());
762 std::ostringstream oss; oss << "DataScopeServerTransaction::notifyKey : MAIN INTERNAL ERROR ! for object id #" << ii << " error during interpretation of cmp(k,wk[i]) !";
763 throw Exception(oss.str());
766 listOfEltToWakeUp.push_back(*it);
768 newList.push_back(*it);
772 for(std::list< KeyWaiter *>::iterator it=listOfEltToWakeUp.begin();it!=listOfEltToWakeUp.end();it++)
773 (*it)->valueJustCome(valueObj);
774 for(std::list< KeyWaiter *>::iterator it=listOfEltToWakeUp.begin();it!=listOfEltToWakeUp.end();it++)
776 _waiting_keys=newList;
779 SALOME::Transaction_ptr DataScopeServerTransaction::addKeyValueInVarHard(const char *varName, const SALOME::ByteVec& key, const SALOME::ByteVec& value)
781 checkVarExistingAndDict(varName);
782 TransactionAddKeyValueHard *ret(new TransactionAddKeyValueHard(this,varName,key,value));
783 CORBA::Object_var obj(ret->activate());
784 return SALOME::Transaction::_narrow(obj);
787 SALOME::Transaction_ptr DataScopeServerTransaction::addKeyValueInVarErrorIfAlreadyExisting(const char *varName, const SALOME::ByteVec& key, const SALOME::ByteVec& value)
789 checkVarExistingAndDict(varName);
790 TransactionAddKeyValueErrorIfAlreadyExisting *ret(new TransactionAddKeyValueErrorIfAlreadyExisting(this,varName,key,value));
791 CORBA::Object_var obj(ret->activate());
792 return SALOME::Transaction::_narrow(obj);
795 SALOME::TransactionMultiKeyAddSession_ptr DataScopeServerTransaction::addMultiKeyValueSession(const char *varName)
797 checkVarExistingAndDict(varName);
798 TransactionMultiKeyAddSession *ret(new TransactionMultiKeyAddSession(this,varName));
799 CORBA::Object_var obj(ret->activate());
800 return SALOME::TransactionMultiKeyAddSession::_narrow(obj);
803 SALOME::Transaction_ptr DataScopeServerTransaction::removeKeyInVarErrorIfNotAlreadyExisting(const char *varName, const SALOME::ByteVec& key)
805 checkVarExistingAndDict(varName);
806 TransactionRemoveKeyInVarErrorIfNotAlreadyExisting *ret(new TransactionRemoveKeyInVarErrorIfNotAlreadyExisting(this,varName,key));
807 CORBA::Object_var obj(ret->activate());
808 return SALOME::Transaction::_narrow(obj);
811 SALOME::TransactionRdWrAccess_ptr DataScopeServerTransaction::createWorkingVarTransac(const char *varName, const SALOME::ByteVec& constValue)
813 std::string varNameCpp(varName);
814 checkNotAlreadyExistingVar(varName);
815 PickelizedPyObjRdWrServer *tmp(new PickelizedPyObjRdWrServer(this,varNameCpp,constValue));
816 CORBA::Object_var obj(tmp->activate());
817 std::pair< SALOME::BasicDataServer_var, BasicDataServer * > p(SALOME::BasicDataServer::_narrow(obj),tmp);
820 TransactionMorphRdWrIntoRdOnly *ret(new TransactionMorphRdWrIntoRdOnly(this,varName));
821 CORBA::Object_var obj2(ret->activate());
822 return SALOME::TransactionRdWrAccess::_narrow(obj2);
825 SALOME::Transaction_ptr DataScopeServerTransaction::killVarTransac(const char *varName)
827 std::string varNameCpp(varName);
828 checkExistingVar(varNameCpp);
830 TransactionKillVar *ret(new TransactionKillVar(this,varName));
831 CORBA::Object_var obj2(ret->activate());
832 return SALOME::Transaction::_narrow(obj2);
835 SALOME::KeyWaiter_ptr DataScopeServerTransaction::waitForKeyInVar(const char *varName, const SALOME::ByteVec& keyVal)
837 PickelizedPyObjServer *pickelObj(checkVarExistingAndDict(varName));
838 KeyWaiter *ret(new KeyWaiter(pickelObj,keyVal));
839 CORBA::Object_var obj(ret->activate());//KeyWaiter instance activated inside a multithread POA contrary to all of objects in SALOMESDS in single thread !
840 return SALOME::KeyWaiter::_narrow(obj);
843 SALOME::KeyWaiter_ptr DataScopeServerTransaction::waitForKeyInVarAndKillIt(const char *varName, const SALOME::ByteVec& keyVal, SALOME::Transaction_out transac)
845 PickelizedPyObjServer *pickelObj(checkVarExistingAndDict(varName));
846 KeyWaiter *ret0(new KeyWaiter(pickelObj,keyVal));
847 CORBA::Object_var obj(ret0->activate());//KeyWaiter instance activated inside a multithread POA contrary to all of objects in SALOMESDS in single thread !
849 TransactionRemoveKeyInVarErrorIfNotAlreadyExisting *ret1(new TransactionRemoveKeyInVarErrorIfNotAlreadyExisting(this,varName,keyVal));
850 CORBA::Object_var obj2(ret1->activate());
851 transac=SALOME::Transaction::_narrow(obj2);
853 return SALOME::KeyWaiter::_narrow(obj);
856 SALOME::ByteVec *DataScopeServerTransaction::waitForMonoThrRev(SALOME::KeyWaiter_ptr kw)
858 PortableServer::ServantBase *ret(0);
861 ret=_poa_for_key_waiter->reference_to_servant(kw);// Warning ref cnt of ret has been incremented !
863 catch(...) { ret=0; }
864 KeyWaiter *retc(dynamic_cast<KeyWaiter *>(ret));
866 throw Exception("DataScopeServerTransaction::invokeMonoThr : internal error 1 !");
867 retc->_remove_ref();// restore the counter after _poa_for_key_waiter->reference_to_servant(kw)
868 SALOME::ByteVec *zeRet(retc->waitForMonoThr());
869 retc->enforcedRelease();
873 SALOME::ByteVec *DataScopeServerTransaction::waitForAndKill(SALOME::KeyWaiter_ptr kw)
875 PortableServer::ServantBase *ret(0);
878 ret=_poa_for_key_waiter->reference_to_servant(kw);// Warning ref cnt of ret has been incremented !
880 catch(...) { ret=0; }
881 KeyWaiter *retc(dynamic_cast<KeyWaiter *>(ret));
883 throw Exception("DataScopeServerTransaction::invokeMonoThr : internal error 1 !");
884 retc->_remove_ref();// restore the counter after _poa_for_key_waiter->reference_to_servant(kw)
885 SALOME::ByteVec *zeRet(retc->waitForAndKill());
886 retc->enforcedRelease();
890 void DataScopeServerTransaction::atomicApply(const SALOME::ListOfTransaction& transactions)
892 std::size_t sz(transactions.length());
895 std::vector< AutoServantPtr<Transaction> > transactionsCpp(sz);
896 for(std::size_t i=0;i<sz;i++)
898 PortableServer::ServantBase *eltBase(0);
902 eltBase=_poa->reference_to_servant(transactions[i]);
903 elt=dynamic_cast<Transaction *>(eltBase);
907 std::ostringstream oss; oss << "DataScopeServerTransaction::atomicApply : the elt #" << i << " is invalid !";
908 throw Exception(oss.str());
912 std::ostringstream oss; oss << "DataScopeServerTransaction::atomicApply : the elt #" << i << " is null ?";
913 throw Exception(oss.str());
916 transactionsCpp[i]=elt;
918 {// important do not merge loops !
919 std::vector<TrustTransaction> transactions2(sz);
920 bool mustRollback(true);
921 for(std::size_t i=0;i<sz;i++)
922 transactions2[i].setTransaction(transactionsCpp[i],&mustRollback);
923 for(std::size_t i=0;i<sz;i++)
924 transactions2[i].operate();
927 for(std::size_t i=0;i<sz;i++)
928 transactionsCpp[i]->notify();
931 DataScopeServerTransaction::~DataScopeServerTransaction()
935 SALOME::RequestSwitcher_ptr DataScopeServerTransaction::getRequestSwitcher()
939 _rs=new RequestSwitcher(_orb,this);
941 CORBA::Object_var obj(_rs->activate());
942 return SALOME::RequestSwitcher::_narrow(obj);