OB 4.20 sp2 -> Java 5.0: pb with callbacks
"Fabrice Bouye" <[email protected]> Fri, 17 Jun 2005 13:13:40 +1100
| Newsgroups | gmane.comp.corba.orbacus |
|---|---|
| Message-ID | <[email protected]> |
For our project we are using a C++ server with ORBacus 4.20 sp2 and Java 5.0 clients using Sun's ORB that are talking to each other. The server monitors an oceanographic data simulator that holds data to be represented as bitmaps on the clients. So far when clients connect to the server and download data all work OK. But we need to use a callback function so the server tells the clients the simulator has achieved a new run; that ways the client will re-download the necessary data and update the display.
In addSeapodymRCListener() when the server call listener->getName(), it works OK and prints the name provided by the client. But each time fireNewRunStarted() is called it crashes with UNKNOW ERROR when it->second->newRunStarted(runNumber) is called.
As of now the Java client-side of newRunStarted() simply does a System.out.println("New run detected" + runNumber) for debugging.
The POA has been correctly activated prior to the ORB start in the server's initialization process.
I suppose that the reference pointer to the listener may get released when exiting addSeapodymRCListener(), and this causes the reference to be invalid in fireNewRunStarted() but I'm puzzled as I cannot detect if there is any error in the way I store/cache the listener.
Thanks for your help.
SeapodymRemote.idl
[...]
interface DSeapodymRCListener {
/** Indicates a new run has started on the server.
* @param runNumber The number of the run.
*/
void newRunStarted(in long runNumber);
string getName();
};
[...]
interface DSeapodymRCService {
////////////////////////
// Client management. //
////////////////////////
/** Registers the given listener.
* <BR>This is typically the first call a client will issue on the server.
* @param listener A listener interrested into Seapodym-RC events.
*/
void addSeapodymRCListener(in DSeapodymRCListener listener);
/** Un register the given listener.
* <BR>This is typically the last call a client will issue on the server.
* @param listener A listener interrested into Seapodym-RC events.
*/
void removeSeapodymRCListener(in DSeapodymRCListener listener);
[...]
Launcher.cpp
[...]
CORBA::Object_var poaObj = orb->resolve_initial_references("RootPOA");
PortableServer::POA_var rootPoa = PortableServer::POA::_narrow(poaObj);
PortableServer::POAManager_var manager = rootPoa->the_POAManager();
[...]
std::cout << "Awaiting client connections... " << std::endl;
manager->activate();
orb->run();
[...]
DSeapodymRCService_Impl.h
[...]
class DSeapodymRCService_Impl : public POA_org::SPC::OFP::SeapodymRemote::DSeapodymRCService, public PortableServer::RefCountServantBase {
private:
/** A map that indexes listener pointers by "clientaddr:port" strings.
*/
typedef std::map<std::string, DSeapodymRCListener_var> ListenerMap;
typedef std::pair<std::string, DSeapodymRCListener_var> ListenerPair;
/** List of registered listeners.
*/
ListenerMap m_listenerMap;
[...]
DSeapodymRCService_Impl.cpp
[...]
void DSeapodymRCService_Impl::addSeapodymRCListener(DSeapodymRCListener_ptr listener) throw (::CORBA::SystemException) {
CORBAUtilities::printClientInfo("addSeapodymRCListener", m_orb);
std::string clientAddr = CORBAUtilities::getClientInfo(m_orb);
std::cout << clientAddr << " " << listener->getName() << std::endl;
if (!clientAddr.empty()) {
m_listenerMap.insert(ListenerPair(clientAddr, listener));
}
}
void DSeapodymRCService_Impl::removeSeapodymRCListener(DSeapodymRCListener_ptr listener) throw(::CORBA::SystemException) {
CORBAUtilities::printClientInfo("removeSeapodymRCListener", m_orb);
std::string clientAddr = CORBAUtilities::getClientInfo(m_orb);
if (!clientAddr.empty()) {
std::cout << "+There are " << m_listenerMap.size() << " listener(s) registered." << std::endl;
ListenerMap::iterator it = m_listenerMap.find(clientAddr);
if (it != m_listenerMap.end()) {
m_listenerMap.erase(it);
}
else {
std::cout << "~Listener for " << clientAddr << " not found!" << std::endl;
}
std::cout << "-There are " << m_listenerMap.size() << " listener(s) registered." << std::endl;
}
}
void DSeapodymRCService_Impl::fireNewRunStarted(int runNumber) {
// Forward to registered remote listeners from first to last.
std::cout << "Notifying " << m_listenerMap.size() << " remote listeners." << std::endl;
for (ListenerMap::iterator it = m_listenerMap.begin() ; it != m_listenerMap.end() ; it++) {
try {
std::cout << "Notifying " << it->first << std::endl;
/** @todo switch to oneway. //
// THIS FAILS and falls into "catch (...)"
it->second->newRunStarted(runNumber);
}
// An error occured.
// Can we get errors when we send oneway methods?
catch (CORBA::Exception& ce) {
std::cerr << "ERROR while notifying " << it->first << " of new run." << std::endl;
// Is the client disconnected?
/** @todo Maybe we should remove this listener from the list. */
}
catch (std::exception& e) {
std::cerr << "ERROR while notifying " << it->first << " of new run." << std::endl;
std::cerr << e.what() << std::endl;
}
catch (...) {
std::cerr << "UNKNOWN ERROR while notifying " << it->first << " of new run." << std::endl;
}
}
}
[...]
----
Fabrice Bouyé ( <http://fabricebouye.cv.fm/> http://fabricebouye.cv.fm/)
Research Officer (Data)
Tel: +687 26 20 00 (Ext 411)
Oceanic Fisheries, Pacific Community
<http://www.spc.int/> http://www.spc.int/
_______________________________________________
OB-Users Mailing List - [email protected]
http://mail.ooc.nf.ca/mailman/listinfo/ob-users
Visit our support FAQ before you send a message.
http://www.orbacus.com/faq/support.html