diff options
82 files changed, 13071 insertions, 27 deletions
diff --git a/cpp/config/Make.rules b/cpp/config/Make.rules index 2e16f720bf5..53ace9f5a08 100644 --- a/cpp/config/Make.rules +++ b/cpp/config/Make.rules @@ -35,7 +35,7 @@ JTC ?= /opt/JTC CXX = c++ CXXFLAGS = -g -ftemplate-depth-128 -fPIC -Wall #CXXFLAGS = -O -DNDEBUG -ftemplate-depth-128 -fPIC -Wall -CPPFLAGS = -I. -I$(includedir) -I$(STLPORT)/stlport -I$(JTC)/include +CPPFLAGS = -I$(includedir) -I$(STLPORT)/stlport -I$(JTC)/include LDFLAGS = -L$(libdir) -L$(STLPORT)/lib -L$(JTC)/lib BASELIBS = -lstlport_gcc_debug -lJTC -lpthread LIBS = -lIce $(BASELIBS) diff --git a/cpp/ice.dsw b/cpp/ice.dsw index 6c7c0f054fc..8378cef46b8 100644 --- a/cpp/ice.dsw +++ b/cpp/ice.dsw @@ -42,7 +42,7 @@ Package=<5> Package=<4>
{{{
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
}}}
@@ -57,7 +57,7 @@ Package=<5> Package=<4>
{{{
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
}}}
@@ -72,7 +72,7 @@ Package=<5> Package=<4>
{{{
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
}}}
@@ -87,7 +87,7 @@ Package=<5> Package=<4>
{{{
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
}}}
@@ -102,7 +102,7 @@ Package=<5> Package=<4>
{{{
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
}}}
@@ -120,7 +120,7 @@ Package=<4> Project_Dep_Name compiler
End Project Dependency
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
}}}
@@ -138,7 +138,7 @@ Package=<4> Project_Dep_Name compiler
End Project Dependency
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
}}}
@@ -162,7 +162,7 @@ Package=<4> Project_Dep_Name interfaceS
End Project Dependency
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
Begin Project Dependency
Project_Dep_Name helloC
@@ -258,7 +258,7 @@ Package=<5> Package=<4>
{{{
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
}}}
@@ -273,7 +273,7 @@ Package=<5> Package=<4>
{{{
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
}}}
@@ -288,7 +288,7 @@ Package=<5> Package=<4>
{{{
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
}}}
@@ -306,7 +306,7 @@ Package=<4> Project_Dep_Name compiler
End Project Dependency
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
}}}
@@ -324,13 +324,13 @@ Package=<4> Project_Dep_Name compiler
End Project Dependency
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
}}}
###############################################################################
-Project: "library"=.\src\library\library.dsp - Package Owner=<4>
+Project: "Ice"=.\src\Ice\Ice.dsp - Package Owner=<4>
Package=<5>
{{{
@@ -354,7 +354,7 @@ Package=<5> Package=<4>
{{{
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
}}}
@@ -369,7 +369,7 @@ Package=<5> Package=<4>
{{{
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
}}}
@@ -384,7 +384,7 @@ Package=<5> Package=<4>
{{{
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
}}}
@@ -399,7 +399,7 @@ Package=<5> Package=<4>
{{{
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
}}}
@@ -414,7 +414,7 @@ Package=<5> Package=<4>
{{{
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
}}}
@@ -444,7 +444,7 @@ Package=<4> Project_Dep_Name compiler
End Project Dependency
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
}}}
@@ -462,7 +462,7 @@ Package=<4> Project_Dep_Name compiler
End Project Dependency
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
}}}
@@ -495,7 +495,7 @@ Package=<4> Project_Dep_Name compiler
End Project Dependency
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
}}}
@@ -513,7 +513,7 @@ Package=<4> Project_Dep_Name compiler
End Project Dependency
Begin Project Dependency
- Project_Dep_Name library
+ Project_Dep_Name Ice
End Project Dependency
}}}
diff --git a/cpp/src/Ice/.depend b/cpp/src/Ice/.depend new file mode 100644 index 00000000000..33f4c0e01e8 --- /dev/null +++ b/cpp/src/Ice/.depend @@ -0,0 +1,42 @@ +Shared.o: Shared.cpp ../../include/Ice/Shared.h ../../include/Ice/Config.h +Stream.o: Stream.cpp ../../include/Ice/Stream.h ../../include/Ice/InstanceF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../../include/Ice/ObjectF.h ../../include/Ice/Buffer.h ../Ice/Instance.h ../../include/Ice/CommunicatorF.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../../include/Ice/PropertiesF.h ../../include/Ice/LoggerF.h ../Ice/TraceLevelsF.h ../../include/Ice/ProxyFactoryF.h ../Ice/ThreadPoolF.h ../../include/Ice/EmitterF.h ../Ice/ValueFactoryManagerF.h ../../include/Ice/ObjectAdapterFactoryF.h ../../include/Ice/PicklerF.h ../../include/Ice/Object.h ../../include/Ice/Proxy.h ../../include/Ice/ReferenceF.h ../../include/Ice/ValueFactory.h ../Ice/ValueFactoryManager.h ../../include/Ice/ValueFactoryF.h ../../include/Ice/LocalException.h +LocalException.o: LocalException.cpp ../../include/Ice/LocalException.h ../../include/Ice/Config.h ../Ice/Network.h +Pickler.o: Pickler.cpp ../../include/Ice/Pickler.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/Config.h ../../include/Ice/ObjectF.h ../../include/Ice/Handle.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../../include/Ice/Stream.h ../../include/Ice/InstanceF.h ../../include/Ice/Buffer.h +PicklerI.o: PicklerI.cpp ../Ice/PicklerI.h ../../include/Ice/Pickler.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/Config.h ../../include/Ice/ObjectF.h ../../include/Ice/Handle.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../../include/Ice/InstanceF.h ../../include/Ice/Stream.h ../../include/Ice/Buffer.h ../../include/Ice/LocalException.h +Properties.o: Properties.cpp ../../include/Ice/Properties.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/Config.h ../../include/Ice/ObjectF.h ../../include/Ice/Handle.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../../include/Ice/Stream.h ../../include/Ice/InstanceF.h ../../include/Ice/Buffer.h +PropertiesI.o: PropertiesI.cpp ../Ice/PropertiesI.h ../../include/Ice/Properties.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/Config.h ../../include/Ice/ObjectF.h ../../include/Ice/Handle.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../../include/Ice/CommunicatorF.h ../../include/Ice/LocalException.h +Logger.o: Logger.cpp ../../include/Ice/Logger.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/Config.h ../../include/Ice/ObjectF.h ../../include/Ice/Handle.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../../include/Ice/Stream.h ../../include/Ice/InstanceF.h ../../include/Ice/Buffer.h +LoggerI.o: LoggerI.cpp ../Ice/LoggerI.h ../../include/Ice/Logger.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/Config.h ../../include/Ice/ObjectF.h ../../include/Ice/Handle.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h +TraceLevels.o: TraceLevels.cpp ../Ice/TraceLevels.h ../Ice/TraceLevelsF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../../include/Ice/PropertiesF.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/ObjectF.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../../include/Ice/Properties.h +TraceUtil.o: TraceUtil.cpp ../Ice/TraceUtil.h ../../include/Ice/LoggerF.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/Config.h ../../include/Ice/ObjectF.h ../../include/Ice/Handle.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../Ice/TraceLevelsF.h ../Ice/Instance.h ../../include/Ice/InstanceF.h ../../include/Ice/CommunicatorF.h ../../include/Ice/PropertiesF.h ../../include/Ice/ProxyFactoryF.h ../Ice/ThreadPoolF.h ../../include/Ice/EmitterF.h ../Ice/ValueFactoryManagerF.h ../../include/Ice/ObjectAdapterFactoryF.h ../../include/Ice/PicklerF.h ../Ice/TraceLevels.h ../../include/Ice/Logger.h ../../include/Ice/Stream.h ../../include/Ice/Buffer.h +Instance.o: Instance.cpp ../Ice/Instance.h ../../include/Ice/InstanceF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../../include/Ice/CommunicatorF.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/ObjectF.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../../include/Ice/PropertiesF.h ../../include/Ice/LoggerF.h ../Ice/TraceLevelsF.h ../../include/Ice/ProxyFactoryF.h ../Ice/ThreadPoolF.h ../../include/Ice/EmitterF.h ../Ice/ValueFactoryManagerF.h ../../include/Ice/ObjectAdapterFactoryF.h ../../include/Ice/PicklerF.h ../Ice/TraceLevels.h ../Ice/ProxyFactory.h ../../include/Ice/ReferenceF.h ../Ice/ThreadPool.h ../Ice/EventHandlerF.h ../Ice/Emitter.h ../Ice/TransceiverF.h ../Ice/ConnectorF.h ../Ice/EndpointF.h ../Ice/EventHandler.h ../../include/Ice/Stream.h ../../include/Ice/Buffer.h ../Ice/ValueFactoryManager.h ../../include/Ice/ValueFactoryF.h ../Ice/ObjectAdapterFactory.h ../../include/Ice/ObjectAdapterF.h ../../include/Ice/LocalException.h ../Ice/LoggerI.h ../../include/Ice/Logger.h ../Ice/PicklerI.h ../../include/Ice/Pickler.h +Communicator.o: Communicator.cpp ../../include/Ice/Communicator.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/Config.h ../../include/Ice/ObjectF.h ../../include/Ice/Handle.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../../include/Ice/LoggerF.h ../../include/Ice/ObjectAdapterF.h ../../include/Ice/PicklerF.h ../../include/Ice/PropertiesF.h ../../include/Ice/ValueFactoryF.h ../../include/Ice/Stream.h ../../include/Ice/InstanceF.h ../../include/Ice/Buffer.h +CommunicatorI.o: CommunicatorI.cpp ../Ice/CommunicatorI.h ../../include/Ice/InstanceF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../../include/Ice/Communicator.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/ObjectF.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../../include/Ice/LoggerF.h ../../include/Ice/ObjectAdapterF.h ../../include/Ice/PicklerF.h ../../include/Ice/PropertiesF.h ../../include/Ice/ValueFactoryF.h ../Ice/PropertiesI.h ../../include/Ice/Properties.h ../../include/Ice/CommunicatorF.h ../Ice/Instance.h ../Ice/TraceLevelsF.h ../../include/Ice/ProxyFactoryF.h ../Ice/ThreadPoolF.h ../../include/Ice/EmitterF.h ../Ice/ValueFactoryManagerF.h ../../include/Ice/ObjectAdapterFactoryF.h ../Ice/ProxyFactory.h ../../include/Ice/ReferenceF.h ../Ice/ThreadPool.h ../Ice/EventHandlerF.h ../../include/Ice/ObjectAdapter.h ../Ice/ValueFactoryManager.h ../Ice/ObjectAdapterFactory.h ../../include/Ice/Logger.h ../../include/Ice/Initialize.h ../../include/Ice/LocalException.h +ObjectAdapter.o: ObjectAdapter.cpp ../../include/Ice/ObjectAdapter.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/Config.h ../../include/Ice/ObjectF.h ../../include/Ice/Handle.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../../include/Ice/CommunicatorF.h ../../include/Ice/Stream.h ../../include/Ice/InstanceF.h ../../include/Ice/Buffer.h +ObjectAdapterI.o: ObjectAdapterI.cpp ../Ice/ObjectAdapterI.h ../../include/Ice/ObjectAdapter.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/Config.h ../../include/Ice/ObjectF.h ../../include/Ice/Handle.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../../include/Ice/CommunicatorF.h ../../include/Ice/InstanceF.h ../../include/Ice/ObjectAdapterFactoryF.h ../../include/Ice/CollectorF.h ../../include/Ice/LocalException.h ../Ice/Instance.h ../../include/Ice/PropertiesF.h ../../include/Ice/LoggerF.h ../Ice/TraceLevelsF.h ../../include/Ice/ProxyFactoryF.h ../Ice/ThreadPoolF.h ../../include/Ice/EmitterF.h ../Ice/ValueFactoryManagerF.h ../../include/Ice/PicklerF.h ../../include/Ice/Proxy.h ../../include/Ice/ReferenceF.h ../Ice/ProxyFactory.h ../Ice/Reference.h ../Ice/EndpointF.h ../Ice/Endpoint.h ../Ice/TransceiverF.h ../Ice/ConnectorF.h ../Ice/AcceptorF.h ../Ice/Collector.h ../../include/Ice/ObjectAdapterF.h ../Ice/EventHandler.h ../Ice/EventHandlerF.h ../../include/Ice/Stream.h ../../include/Ice/Buffer.h ../../include/Ice/Functional.h +ObjectAdapterFactory.o: ObjectAdapterFactory.cpp ../Ice/ObjectAdapterFactory.h ../../include/Ice/ObjectAdapterFactoryF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../../include/Ice/InstanceF.h ../../include/Ice/ObjectAdapterF.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/ObjectF.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../Ice/ObjectAdapterI.h ../../include/Ice/ObjectAdapter.h ../../include/Ice/CommunicatorF.h ../../include/Ice/CollectorF.h ../../include/Ice/LocalException.h ../../include/Ice/Functional.h ../Ice/Instance.h ../../include/Ice/PropertiesF.h ../../include/Ice/LoggerF.h ../Ice/TraceLevelsF.h ../../include/Ice/ProxyFactoryF.h ../Ice/ThreadPoolF.h ../../include/Ice/EmitterF.h ../Ice/ValueFactoryManagerF.h ../../include/Ice/PicklerF.h +ValueFactory.o: ValueFactory.cpp ../../include/Ice/ValueFactory.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/Config.h ../../include/Ice/ObjectF.h ../../include/Ice/Handle.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../../include/Ice/Stream.h ../../include/Ice/InstanceF.h ../../include/Ice/Buffer.h +ValueFactoryManager.o: ValueFactoryManager.cpp ../Ice/ValueFactoryManager.h ../Ice/ValueFactoryManagerF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../../include/Ice/ValueFactoryF.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/ObjectF.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../../include/Ice/ValueFactory.h +Endpoint.o: Endpoint.cpp ../Ice/Endpoint.h ../Ice/EndpointF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../../include/Ice/InstanceF.h ../Ice/TransceiverF.h ../Ice/ConnectorF.h ../Ice/AcceptorF.h ../../include/Ice/Shared.h ../Ice/Network.h ../Ice/TcpAcceptor.h ../Ice/TraceLevelsF.h ../../include/Ice/LoggerF.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/ObjectF.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../Ice/Acceptor.h ../Ice/TcpConnector.h ../Ice/Connector.h ../Ice/TcpTransceiver.h ../Ice/Transceiver.h ../Ice/SslAcceptor.h ../Ice/SslConnector.h ../Ice/SslTransceiver.h ../Ice/UdpTransceiver.h ../../include/Ice/Stream.h ../../include/Ice/Buffer.h ../../include/Ice/LocalException.h +Reference.o: Reference.cpp ../Ice/Reference.h ../../include/Ice/ReferenceF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../Ice/EndpointF.h ../../include/Ice/InstanceF.h ../../include/Ice/Shared.h ../Ice/Endpoint.h ../Ice/TransceiverF.h ../Ice/ConnectorF.h ../Ice/AcceptorF.h ../../include/Ice/Stream.h ../../include/Ice/ObjectF.h ../../include/Ice/Buffer.h ../../include/Ice/LocalException.h +LocalObject.o: LocalObject.cpp ../../include/Ice/LocalObject.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/Shared.h +Object.o: Object.cpp ../../include/Ice/Object.h ../../include/Ice/ObjectF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../../include/Ice/Proxy.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/ProxyFactoryF.h ../../include/Ice/EmitterF.h ../../include/Ice/ReferenceF.h ../../include/Ice/Shared.h ../../include/Ice/Incoming.h ../../include/Ice/ObjectAdapterF.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/InstanceF.h ../../include/Ice/Stream.h ../../include/Ice/Buffer.h +ProxyFactory.o: ProxyFactory.cpp ../Ice/ProxyFactory.h ../../include/Ice/ProxyFactoryF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../../include/Ice/InstanceF.h ../../include/Ice/ReferenceF.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/Shared.h ../Ice/Instance.h ../../include/Ice/CommunicatorF.h ../../include/Ice/ObjectF.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/PropertiesF.h ../../include/Ice/LoggerF.h ../Ice/TraceLevelsF.h ../Ice/ThreadPoolF.h ../../include/Ice/EmitterF.h ../Ice/ValueFactoryManagerF.h ../../include/Ice/ObjectAdapterFactoryF.h ../../include/Ice/PicklerF.h ../../include/Ice/Proxy.h ../Ice/Reference.h ../Ice/EndpointF.h ../Ice/Endpoint.h ../Ice/TransceiverF.h ../Ice/ConnectorF.h ../Ice/AcceptorF.h ../../include/Ice/Stream.h ../../include/Ice/Buffer.h +Proxy.o: Proxy.cpp ../../include/Ice/Proxy.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/Config.h ../../include/Ice/ProxyFactoryF.h ../../include/Ice/Handle.h ../../include/Ice/EmitterF.h ../../include/Ice/ReferenceF.h ../../include/Ice/Shared.h ../Ice/ProxyFactory.h ../../include/Ice/InstanceF.h ../../include/Ice/Object.h ../../include/Ice/ObjectF.h ../Ice/ObjectAdapterFactory.h ../../include/Ice/ObjectAdapterFactoryF.h ../../include/Ice/ObjectAdapterF.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Outgoing.h ../../include/Ice/Stream.h ../../include/Ice/Buffer.h ../Ice/Reference.h ../Ice/EndpointF.h ../Ice/Endpoint.h ../Ice/TransceiverF.h ../Ice/ConnectorF.h ../Ice/AcceptorF.h ../Ice/Instance.h ../../include/Ice/CommunicatorF.h ../../include/Ice/PropertiesF.h ../../include/Ice/LoggerF.h ../Ice/TraceLevelsF.h ../Ice/ThreadPoolF.h ../Ice/ValueFactoryManagerF.h ../../include/Ice/PicklerF.h ../../include/Ice/Logger.h ../Ice/TraceLevels.h ../Ice/Emitter.h ../Ice/EventHandler.h ../Ice/EventHandlerF.h ../../include/Ice/LocalException.h ../../include/Ice/Functional.h +Outgoing.o: Outgoing.cpp ../../include/Ice/Outgoing.h ../../include/Ice/EmitterF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../../include/Ice/ReferenceF.h ../../include/Ice/Stream.h ../../include/Ice/InstanceF.h ../../include/Ice/ObjectF.h ../../include/Ice/Buffer.h ../../include/Ice/Object.h ../../include/Ice/Proxy.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/ProxyFactoryF.h ../../include/Ice/Shared.h ../Ice/Emitter.h ../Ice/TransceiverF.h ../Ice/ConnectorF.h ../Ice/ThreadPoolF.h ../Ice/EndpointF.h ../Ice/TraceLevelsF.h ../../include/Ice/LoggerF.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../Ice/EventHandler.h ../Ice/EventHandlerF.h ../Ice/Reference.h ../../include/Ice/LocalException.h +Incoming.o: Incoming.cpp ../../include/Ice/Incoming.h ../../include/Ice/ObjectAdapterF.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/Config.h ../../include/Ice/ObjectF.h ../../include/Ice/Handle.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../../include/Ice/InstanceF.h ../../include/Ice/Stream.h ../../include/Ice/Buffer.h ../../include/Ice/ObjectAdapter.h ../../include/Ice/CommunicatorF.h ../../include/Ice/Object.h ../../include/Ice/Proxy.h ../../include/Ice/ProxyFactoryF.h ../../include/Ice/EmitterF.h ../../include/Ice/ReferenceF.h ../../include/Ice/LocalException.h +Emitter.o: Emitter.cpp ../Ice/Emitter.h ../../include/Ice/EmitterF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../../include/Ice/InstanceF.h ../Ice/TransceiverF.h ../Ice/ConnectorF.h ../Ice/ThreadPoolF.h ../Ice/EndpointF.h ../Ice/TraceLevelsF.h ../../include/Ice/LoggerF.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/ObjectF.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../Ice/EventHandler.h ../Ice/EventHandlerF.h ../../include/Ice/Stream.h ../../include/Ice/Buffer.h ../Ice/Instance.h ../../include/Ice/CommunicatorF.h ../../include/Ice/PropertiesF.h ../../include/Ice/ProxyFactoryF.h ../Ice/ValueFactoryManagerF.h ../../include/Ice/ObjectAdapterFactoryF.h ../../include/Ice/PicklerF.h ../../include/Ice/Logger.h ../Ice/TraceLevels.h ../Ice/TraceUtil.h ../Ice/Transceiver.h ../Ice/Connector.h ../Ice/ThreadPool.h ../Ice/Endpoint.h ../Ice/AcceptorF.h ../../include/Ice/Outgoing.h ../../include/Ice/ReferenceF.h ../../include/Ice/LocalException.h ../../include/Ice/Functional.h +Collector.o: Collector.cpp ../Ice/Collector.h ../../include/Ice/CollectorF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../../include/Ice/InstanceF.h ../Ice/TransceiverF.h ../Ice/AcceptorF.h ../Ice/ThreadPoolF.h ../../include/Ice/ObjectAdapterF.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/ObjectF.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../Ice/EndpointF.h ../Ice/TraceLevelsF.h ../../include/Ice/LoggerF.h ../Ice/EventHandler.h ../Ice/EventHandlerF.h ../../include/Ice/Stream.h ../../include/Ice/Buffer.h ../Ice/Instance.h ../../include/Ice/CommunicatorF.h ../../include/Ice/PropertiesF.h ../../include/Ice/ProxyFactoryF.h ../../include/Ice/EmitterF.h ../Ice/ValueFactoryManagerF.h ../../include/Ice/ObjectAdapterFactoryF.h ../../include/Ice/PicklerF.h ../../include/Ice/Logger.h ../Ice/TraceUtil.h ../Ice/Transceiver.h ../Ice/Acceptor.h ../Ice/ThreadPool.h ../../include/Ice/ObjectAdapter.h ../Ice/Endpoint.h ../Ice/ConnectorF.h ../../include/Ice/Incoming.h ../../include/Ice/LocalException.h ../../include/Ice/Functional.h +Network.o: Network.cpp ../Ice/Network.h ../../include/Ice/Config.h ../../include/Ice/LocalException.h +ThreadPool.o: ThreadPool.cpp ../Ice/ThreadPool.h ../Ice/ThreadPoolF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../../include/Ice/InstanceF.h ../Ice/EventHandlerF.h ../../include/Ice/Shared.h ../Ice/EventHandler.h ../../include/Ice/Stream.h ../../include/Ice/ObjectF.h ../../include/Ice/Buffer.h ../Ice/Network.h ../../include/Ice/LocalException.h ../Ice/Instance.h ../../include/Ice/CommunicatorF.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/PropertiesF.h ../../include/Ice/LoggerF.h ../Ice/TraceLevelsF.h ../../include/Ice/ProxyFactoryF.h ../../include/Ice/EmitterF.h ../Ice/ValueFactoryManagerF.h ../../include/Ice/ObjectAdapterFactoryF.h ../../include/Ice/PicklerF.h ../../include/Ice/Properties.h ../../include/Ice/Functional.h +EventHandler.o: EventHandler.cpp ../Ice/EventHandler.h ../Ice/EventHandlerF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../../include/Ice/InstanceF.h ../Ice/ThreadPoolF.h ../../include/Ice/Shared.h ../../include/Ice/Stream.h ../../include/Ice/ObjectF.h ../../include/Ice/Buffer.h ../Ice/Instance.h ../../include/Ice/CommunicatorF.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/PropertiesF.h ../../include/Ice/LoggerF.h ../Ice/TraceLevelsF.h ../../include/Ice/ProxyFactoryF.h ../../include/Ice/EmitterF.h ../Ice/ValueFactoryManagerF.h ../../include/Ice/ObjectAdapterFactoryF.h ../../include/Ice/PicklerF.h +Connector.o: Connector.cpp ../Ice/Connector.h ../Ice/ConnectorF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../Ice/TransceiverF.h ../../include/Ice/Shared.h +Acceptor.o: Acceptor.cpp ../Ice/Acceptor.h ../Ice/AcceptorF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../Ice/TransceiverF.h ../../include/Ice/Shared.h +Transceiver.o: Transceiver.cpp ../Ice/Transceiver.h ../Ice/TransceiverF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../../include/Ice/Shared.h +TcpConnector.o: TcpConnector.cpp ../Ice/TcpConnector.h ../Ice/TransceiverF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../../include/Ice/InstanceF.h ../Ice/TraceLevelsF.h ../../include/Ice/LoggerF.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/ObjectF.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../Ice/Connector.h ../Ice/ConnectorF.h ../Ice/TcpTransceiver.h ../Ice/Transceiver.h ../Ice/Instance.h ../../include/Ice/CommunicatorF.h ../../include/Ice/PropertiesF.h ../../include/Ice/ProxyFactoryF.h ../Ice/ThreadPoolF.h ../../include/Ice/EmitterF.h ../Ice/ValueFactoryManagerF.h ../../include/Ice/ObjectAdapterFactoryF.h ../../include/Ice/PicklerF.h ../Ice/TraceLevels.h ../../include/Ice/Logger.h ../Ice/Network.h ../../include/Ice/LocalException.h +TcpAcceptor.o: TcpAcceptor.cpp ../Ice/TcpAcceptor.h ../Ice/TransceiverF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../../include/Ice/InstanceF.h ../Ice/TraceLevelsF.h ../../include/Ice/LoggerF.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/ObjectF.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../Ice/Acceptor.h ../Ice/AcceptorF.h ../Ice/TcpTransceiver.h ../Ice/Transceiver.h ../Ice/Instance.h ../../include/Ice/CommunicatorF.h ../../include/Ice/PropertiesF.h ../../include/Ice/ProxyFactoryF.h ../Ice/ThreadPoolF.h ../../include/Ice/EmitterF.h ../Ice/ValueFactoryManagerF.h ../../include/Ice/ObjectAdapterFactoryF.h ../../include/Ice/PicklerF.h ../Ice/TraceLevels.h ../../include/Ice/Logger.h ../Ice/Network.h ../../include/Ice/LocalException.h +TcpTransceiver.o: TcpTransceiver.cpp ../Ice/TcpTransceiver.h ../../include/Ice/InstanceF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../Ice/TraceLevelsF.h ../../include/Ice/LoggerF.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/ObjectF.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../Ice/Transceiver.h ../Ice/TransceiverF.h ../Ice/Instance.h ../../include/Ice/CommunicatorF.h ../../include/Ice/PropertiesF.h ../../include/Ice/ProxyFactoryF.h ../Ice/ThreadPoolF.h ../../include/Ice/EmitterF.h ../Ice/ValueFactoryManagerF.h ../../include/Ice/ObjectAdapterFactoryF.h ../../include/Ice/PicklerF.h ../Ice/TraceLevels.h ../../include/Ice/Logger.h ../../include/Ice/Buffer.h ../Ice/Network.h ../../include/Ice/LocalException.h +SslConnector.o: SslConnector.cpp ../Ice/SslConnector.h ../Ice/TransceiverF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../../include/Ice/InstanceF.h ../Ice/TraceLevelsF.h ../../include/Ice/LoggerF.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/ObjectF.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../Ice/Connector.h ../Ice/ConnectorF.h ../Ice/SslTransceiver.h ../Ice/Transceiver.h ../Ice/Instance.h ../../include/Ice/CommunicatorF.h ../../include/Ice/PropertiesF.h ../../include/Ice/ProxyFactoryF.h ../Ice/ThreadPoolF.h ../../include/Ice/EmitterF.h ../Ice/ValueFactoryManagerF.h ../../include/Ice/ObjectAdapterFactoryF.h ../../include/Ice/PicklerF.h ../Ice/TraceLevels.h ../../include/Ice/Logger.h ../Ice/Network.h ../../include/Ice/LocalException.h +SslAcceptor.o: SslAcceptor.cpp ../Ice/SslAcceptor.h ../Ice/TransceiverF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../../include/Ice/InstanceF.h ../Ice/TraceLevelsF.h ../../include/Ice/LoggerF.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/ObjectF.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../Ice/Acceptor.h ../Ice/AcceptorF.h ../Ice/SslTransceiver.h ../Ice/Transceiver.h ../Ice/Instance.h ../../include/Ice/CommunicatorF.h ../../include/Ice/PropertiesF.h ../../include/Ice/ProxyFactoryF.h ../Ice/ThreadPoolF.h ../../include/Ice/EmitterF.h ../Ice/ValueFactoryManagerF.h ../../include/Ice/ObjectAdapterFactoryF.h ../../include/Ice/PicklerF.h ../Ice/TraceLevels.h ../../include/Ice/Logger.h ../Ice/Network.h ../../include/Ice/LocalException.h +SslTransceiver.o: SslTransceiver.cpp ../Ice/SslTransceiver.h ../../include/Ice/InstanceF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../Ice/TraceLevelsF.h ../../include/Ice/LoggerF.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/ObjectF.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../Ice/Transceiver.h ../Ice/TransceiverF.h ../Ice/Instance.h ../../include/Ice/CommunicatorF.h ../../include/Ice/PropertiesF.h ../../include/Ice/ProxyFactoryF.h ../Ice/ThreadPoolF.h ../../include/Ice/EmitterF.h ../Ice/ValueFactoryManagerF.h ../../include/Ice/ObjectAdapterFactoryF.h ../../include/Ice/PicklerF.h ../Ice/TraceLevels.h ../../include/Ice/Logger.h ../../include/Ice/Buffer.h ../Ice/Network.h ../../include/Ice/LocalException.h +UdpTransceiver.o: UdpTransceiver.cpp ../Ice/UdpTransceiver.h ../../include/Ice/InstanceF.h ../../include/Ice/Handle.h ../../include/Ice/Config.h ../Ice/TraceLevelsF.h ../../include/Ice/LoggerF.h ../../include/Ice/ProxyF.h ../../include/Ice/ProxyHandle.h ../../include/Ice/ObjectF.h ../../include/Ice/LocalObjectF.h ../../include/Ice/Native.h ../../include/Ice/LocalObject.h ../../include/Ice/Shared.h ../Ice/Transceiver.h ../Ice/TransceiverF.h ../Ice/Instance.h ../../include/Ice/CommunicatorF.h ../../include/Ice/PropertiesF.h ../../include/Ice/ProxyFactoryF.h ../Ice/ThreadPoolF.h ../../include/Ice/EmitterF.h ../Ice/ValueFactoryManagerF.h ../../include/Ice/ObjectAdapterFactoryF.h ../../include/Ice/PicklerF.h ../Ice/TraceLevels.h ../../include/Ice/Logger.h ../../include/Ice/Buffer.h ../Ice/Network.h ../../include/Ice/LocalException.h diff --git a/cpp/src/Ice/Acceptor.cpp b/cpp/src/Ice/Acceptor.cpp new file mode 100644 index 00000000000..70a95992071 --- /dev/null +++ b/cpp/src/Ice/Acceptor.cpp @@ -0,0 +1,18 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/Acceptor.h> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +void IceInternal::incRef(Acceptor* p) { p->__incRef(); } +void IceInternal::decRef(Acceptor* p) { p->__decRef(); } diff --git a/cpp/src/Ice/Acceptor.h b/cpp/src/Ice/Acceptor.h new file mode 100644 index 00000000000..9c26905334b --- /dev/null +++ b/cpp/src/Ice/Acceptor.h @@ -0,0 +1,40 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_ACCEPTOR_H +#define ICE_ACCEPTOR_H + +#include <Ice/AcceptorF.h> +#include <Ice/TransceiverF.h> +#include <Ice/Shared.h> + +namespace IceInternal +{ + +class Acceptor : public Shared +{ +public: + + virtual int fd() = 0; + virtual void close() = 0; + virtual void shutdown() = 0; + virtual void listen() = 0; + virtual TransceiverPtr accept(int) = 0; + virtual std::string toString() const = 0; + +protected: + + Acceptor() { } + virtual ~Acceptor() { } +}; + +} + +#endif diff --git a/cpp/src/Ice/AcceptorF.h b/cpp/src/Ice/AcceptorF.h new file mode 100644 index 00000000000..153f513a6e5 --- /dev/null +++ b/cpp/src/Ice/AcceptorF.h @@ -0,0 +1,26 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_ACCEPTOR_F_H +#define ICE_ACCEPTOR_F_H + +#include <Ice/Handle.h> + +namespace IceInternal +{ + +class Acceptor; +void incRef(Acceptor*); +void decRef(Acceptor*); +typedef IceInternal::Handle<Acceptor> AcceptorPtr; + +} + +#endif diff --git a/cpp/src/Ice/Collector.cpp b/cpp/src/Ice/Collector.cpp new file mode 100644 index 00000000000..4557f974f3f --- /dev/null +++ b/cpp/src/Ice/Collector.cpp @@ -0,0 +1,692 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/Collector.h> +#include <Ice/Instance.h> +#include <Ice/Logger.h> +#include <Ice/TraceUtil.h> +#include <Ice/Transceiver.h> +#include <Ice/Acceptor.h> +#include <Ice/ThreadPool.h> +#include <Ice/ObjectAdapter.h> +#include <Ice/Endpoint.h> +#include <Ice/Incoming.h> +#include <Ice/LocalException.h> +#include <Ice/Functional.h> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +void IceInternal::incRef(Collector* p) { p->__incRef(); } +void IceInternal::decRef(Collector* p) { p->__decRef(); } + +void IceInternal::incRef(CollectorFactory* p) { p->__incRef(); } +void IceInternal::decRef(CollectorFactory* p) { p->__decRef(); } + +void +IceInternal::Collector::destroy() +{ + JTCSyncT<JTCRecursiveMutex> sync(*this); + setState(StateClosing); +} + +bool +IceInternal::Collector::destroyed() const +{ + JTCSyncT<JTCRecursiveMutex> sync(*this); + return _state >= StateClosing; +} + +void +IceInternal::Collector::hold() +{ + JTCSyncT<JTCRecursiveMutex> sync(*this); + setState(StateHolding); +} + +void +IceInternal::Collector::activate() +{ + JTCSyncT<JTCRecursiveMutex> sync(*this); + setState(StateActive); +} + +bool +IceInternal::Collector::server() const +{ + return true; +} + +bool +IceInternal::Collector::readable() const +{ + return true; +} + +void +IceInternal::Collector::read(Stream& stream) +{ + _transceiver->read(stream, 0); +} + +void +IceInternal::Collector::message(Stream& stream) +{ + Incoming in(_instance, _adapter); + Stream* os = in.os(); + bool invoke = false; + bool response = false; + + { + JTCSyncT<JTCRecursiveMutex> sync(*this); + + _threadPool->promoteFollower(); + + if (_state != StateActive && _state != StateClosing) + { + return; + } + + try + { + assert(stream.i == stream.b.end()); + stream.i = stream.b.begin() + 3; + Byte messageType; + stream.read(messageType); + stream.i = stream.b.begin() + 8; + + // + // Write partial message header + // + os->write(bigendian); + os->write(Byte(0)); // Protocol version + os->write(Byte(0)); // Encoding version + + switch (messageType) + { + case 0: // Request + { + if (_state == StateClosing) + { + traceRequest("received request during closing\n" + "(ignored by server, client will retry)", + stream, _logger, _traceLevels); + } + else + { + traceRequest("received request", + stream, _logger, _traceLevels); + invoke = true; + Int requestId; + stream.read(requestId); + if (!_endpoint->oneway() && + requestId != 0) // 0 means oneway + { + response = true; + ++_responseCount; + os->write(Byte(1)); // Message type (reply) + os->write(Int(0)); // Message size (placeholder) + os->write(requestId); // Request id + } + } + break; + } + + case 1: // Reply + { + traceReply("received reply on server side\n" + "(invalid, closing connection)", + stream, _logger, _traceLevels); + throw InvalidMessageException(__FILE__, __LINE__); + break; + } + + case 2: // CloseConnection + { + traceHeader("received close connection on server side\n" + "(invalid, closing connection)", + stream, _logger, _traceLevels); + throw InvalidMessageException(__FILE__, __LINE__); + break; + } + + default: + { + traceHeader("received unknown message\n" + "(invalid, closing connection)", + stream, _logger, _traceLevels); + throw UnknownMessageException(__FILE__, __LINE__); + break; + } + } + } + catch(const ConnectionLostException&) + { + setState(StateClosed); // Connection drop from client is ok + return; + } + catch(const LocalException& ex) + { + warning(ex); + setState(StateClosed); + return; + } + } + + if (invoke) + { + try + { + in.invoke(stream); + } + catch(const LocalException& ex) + { + JTCSyncT<JTCRecursiveMutex> sync(*this); + warning(ex); + setState(StateClosed); + return; + } + catch(...) + { + JTCSyncT<JTCRecursiveMutex> sync(*this); + string s("server exception:\n"); + s += "unknown exception (no further information available)\n"; + s += _transceiver->toString(); + _logger->warning(s); + setState(StateClosed); + return; + } + } + + if (response) + { + JTCSyncT<JTCRecursiveMutex> sync(*this); + + if (_state != StateActive && _state != StateClosing) + { + return; + } + + try + { + os->i = os->b.begin(); + + // + // Fill in the message size + // + const Byte* p; + Int sz = os->b.size(); + p = reinterpret_cast<Byte*>(&sz); + copy(p, p + sizeof(Int), os->i + 4); + + traceReply("sending reply", *os, _logger, _traceLevels); + _transceiver->write(*os, _endpoint->timeout()); + + --_responseCount; + + if (_state == StateClosing && _responseCount == 0) + { + closeConnection(); + } + } + catch(const ConnectionLostException&) + { + setState(StateClosed); // Connection drop from client is ok + return; + } + catch(const LocalException& ex) + { + warning(ex); + setState(StateClosed); + return; + } + } +} + +void +IceInternal::Collector::exception(const LocalException& ex) +{ + JTCSyncT<JTCRecursiveMutex> sync(*this); + + if (_state != StateActive && _state != StateClosing) + { + return; + } + + if (!dynamic_cast<const ConnectionLostException*>(&ex)) + { + warning(ex); + } + + setState(StateClosed); +} + +void +IceInternal::Collector::finished() +{ + JTCSyncT<JTCRecursiveMutex> sync(*this); + + // + // We also unregister with the thread poool if we go to holding + // state, but in this case we may not close the connection. + // + if (_state == StateClosed) + { + _transceiver->close(); + } +} + +IceInternal::Collector::Collector(const InstancePtr& instance, + const ObjectAdapterPtr& adapter, + const TransceiverPtr& transceiver, + const EndpointPtr& endpoint) : + EventHandler(instance), + _adapter(adapter), + _transceiver(transceiver), + _endpoint(endpoint), + _responseCount(0), + _state(StateHolding) +{ +#ifndef ICE_NO_TRACE + _traceLevels = _instance->traceLevels(); + _logger = _instance->logger(); +#endif + + _threadPool = _instance->threadPool(); +} + +IceInternal::Collector::~Collector() +{ + assert(_state == StateClosed); +} + +void +IceInternal::Collector::setState(State state) +{ + if (_endpoint->oneway() && state == StateClosing) + { + state = StateClosed; + } + + if (_state == state) // Don't switch twice + { + return; + } + + switch (state) + { + case StateActive: + { + if (_state != StateHolding) // Can only switch from holding to active + { + return; + } + + _threadPool->_register(_transceiver->fd(), this); + break; + } + + case StateHolding: + { + if (_state != StateActive) // Can only switch from active to holding + { + return; + } + + _threadPool->unregister(_transceiver->fd()); + break; + } + + case StateClosing: + { + if (_state == StateClosed) // Can't change back from closed + { + return; + } + + if (_responseCount == 0) + { + try + { + closeConnection(); + } + catch(const ConnectionLostException&) + { + state = StateClosed; + setState(state); // Connection drop from client is ok + } + catch(const LocalException& ex) + { + warning(ex); + state = StateClosed; + setState(state); + } + } + + // + // We need to continue to read data in closing state + // + if (_state == StateHolding) + { + _threadPool->_register(_transceiver->fd(), this); + } + break; + } + + case StateClosed: + { + // + // If we come from holding state, we are already unregistered, + // so we can close right away. + // + if (_state == StateHolding) + { + _transceiver->close(); + } + else + { + _threadPool->unregister(_transceiver->fd()); + } + break; + } + } + + _state = state; +} + +void +IceInternal::Collector::closeConnection() +{ + Stream os(_instance); + os.write(bigendian); + os.write(Byte(0)); // Protocol version + os.write(Byte(0)); // Encoding version + os.write(Byte(2)); // Message type = CloseConnection + os.write(Int(8)); // Message size + os.i = os.b.begin(); + traceHeader("sending close connection", os, _logger, _traceLevels); + _transceiver->write(os, _endpoint->timeout()); + _transceiver->shutdown(); +} + +void +IceInternal::Collector::warning(const LocalException& ex) const +{ + string s("server exception:\n"); + s += ex.toString(); + s += "\n"; + s += _transceiver->toString(); + _logger->warning(s); +} + +void +IceInternal::CollectorFactory::destroy() +{ + JTCSyncT<JTCMutex> sync(*this); + setState(StateClosed); +} + +void +IceInternal::CollectorFactory::hold() +{ + JTCSyncT<JTCMutex> sync(*this); + setState(StateHolding); +} + +void +IceInternal::CollectorFactory::activate() +{ + JTCSyncT<JTCMutex> sync(*this); + setState(StateActive); +} + +EndpointPtr +IceInternal::CollectorFactory::endpoint() const +{ + return _endpoint; +} + +bool +IceInternal::CollectorFactory::equivalent(const EndpointPtr& endp) const +{ + if (_transceiver) + { + return endp->equivalent(_transceiver); + } + + assert(_acceptor); + return endp->equivalent(_acceptor); +} + +bool +IceInternal::CollectorFactory::server() const +{ + return true; +} + +bool +IceInternal::CollectorFactory::readable() const +{ + return false; +} + +void +IceInternal::CollectorFactory::read(Stream&) +{ + assert(false); // Must not be called +} + +void +IceInternal::CollectorFactory::message(Stream&) +{ + JTCSyncT<JTCMutex> sync(*this); + + _threadPool->promoteFollower(); + + if (_state != StateActive) + { + return; + } + + // + // First reap destroyed collectors + // + // Can't use _collectors.remove_if(constMemFun(...)), because VC++ + // doesn't support member templates :-( + _collectors.erase(remove_if(_collectors.begin(), _collectors.end(), constMemFun(&Collector::destroyed)), + _collectors.end()); + + // + // Now accept a new connection and create a new CollectorPtr + // + try + { + TransceiverPtr transceiver = _acceptor->accept(0); + CollectorPtr collector = new Collector(_instance, _adapter, transceiver, _endpoint); + collector->activate(); + _collectors.push_back(collector); + } + catch(const TimeoutException&) + { + // Ignore timeouts + } + catch(const LocalException& ex) + { + warning(ex); + destroy(); + } +} + +void +IceInternal::CollectorFactory::exception(const LocalException&) +{ + assert(false); // Must not be called +} + +void +IceInternal::CollectorFactory::finished() +{ + JTCSyncT<JTCMutex> sync(*this); + + // + // We also unregister with the thread poool if we go to holding + // state, but in this case we may not close the acceptor. + // + if (_state == StateClosed) + { + _acceptor->shutdown(); + clearBacklog(); + _acceptor->close(); + } +} + +IceInternal::CollectorFactory::CollectorFactory(const InstancePtr& instance, + const ObjectAdapterPtr& adapter, + const EndpointPtr& endpoint) : + EventHandler(instance), + _adapter(adapter), + _endpoint(endpoint), + _state(StateHolding) +{ +#ifndef ICE_NO_TRACE + _traceLevels = _instance->traceLevels(); + _logger = _instance->logger(); +#endif + + try + { + _transceiver = endpoint->serverTransceiver(_instance); + if (_transceiver) + { + CollectorPtr collector = new Collector(_instance, _adapter, _transceiver, _endpoint); + _collectors.push_back(collector); + } + else + { + _acceptor = endpoint->acceptor(_instance); + assert(_acceptor); + _acceptor->listen(); + _threadPool = _instance->threadPool(); + } + } + catch(...) + { + setState(StateClosed); + throw; + } +} + +IceInternal::CollectorFactory::~CollectorFactory() +{ + assert(_state == StateClosed); +} + +void +IceInternal::CollectorFactory::setState(State state) +{ + if (_state == state) // Don't switch twice + { + return; + } + + switch (state) + { + case StateActive: + { + if (_state != StateHolding) // Can only switch from holding to active + { + return; + } + + if (_threadPool) + { + _threadPool->_register(_acceptor->fd(), this); + } + + for_each(_collectors.begin(), _collectors.end(), voidMemFun(&Collector::activate)); + break; + } + + case StateHolding: + { + if (_state != StateActive) // Can only switch from active to holding + { + return; + } + + if (_threadPool) + { + _threadPool->unregister(_acceptor->fd()); + } + + for_each(_collectors.begin(), _collectors.end(), voidMemFun(&Collector::hold)); + break; + } + + case StateClosed: + { + if (_threadPool) + { + // + // If we come from holding state, we are already + // unregistered, so we can close right away. + // + if (_state == StateHolding) + { + _acceptor->shutdown(); + clearBacklog(); + _acceptor->close(); + } + else + { + _threadPool->unregister(_acceptor->fd()); + } + } + for_each(_collectors.begin(), _collectors.end(), voidMemFun(&Collector::destroy)); + _collectors.clear(); + break; + } + } + + _state = state; +} + +void +IceInternal::CollectorFactory::clearBacklog() +{ + // + // Clear listen() backlog properly by accepting all queued + // connections, and then shutting them down. + // + while (true) + { + try + { + TransceiverPtr transceiver = _acceptor->accept(0); + CollectorPtr collector = new Collector(_instance, _adapter, transceiver, _endpoint); + collector->destroy(); + } + catch(const LocalException&) + { + break; + } + } +} + +void +IceInternal::CollectorFactory::warning(const LocalException& ex) const +{ + string s("server exception:\n"); + s += ex.toString(); + s += "\n"; + s += _acceptor->toString(); + _logger->warning(s); +} diff --git a/cpp/src/Ice/Collector.h b/cpp/src/Ice/Collector.h new file mode 100644 index 00000000000..dcccc37a04c --- /dev/null +++ b/cpp/src/Ice/Collector.h @@ -0,0 +1,146 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_COLLECTOR_H +#define ICE_COLLECTOR_H + +#include <Ice/CollectorF.h> +#include <Ice/InstanceF.h> +#include <Ice/TransceiverF.h> +#include <Ice/AcceptorF.h> +#include <Ice/ThreadPoolF.h> +#include <Ice/ObjectAdapterF.h> +#include <Ice/EndpointF.h> +#include <Ice/TraceLevelsF.h> +#include <Ice/LoggerF.h> +#include <Ice/EventHandler.h> +#include <list> + +namespace Ice +{ + +class LocalException; +class ObjectAdapterI; + +} + +namespace IceInternal +{ + +class Incoming; + +class Collector : public EventHandler, public JTCRecursiveMutex +{ +public: + + void destroy(); + bool destroyed() const; + void hold(); + void activate(); + void prepareReply(Incoming*); + void sendReply(Incoming*); + + // + // Operations from EventHandler + // + virtual bool server() const; + virtual bool readable() const; + virtual void read(Stream&); + virtual void message(Stream&); + virtual void exception(const ::Ice::LocalException&); + virtual void finished(); + +private: + + Collector(const InstancePtr&, const ::Ice::ObjectAdapterPtr&, + const TransceiverPtr&, const EndpointPtr&); + virtual ~Collector(); + friend class CollectorFactory; + + enum State + { + StateActive, + StateHolding, + StateClosing, + StateClosed + }; + + void setState(State); + void closeConnection(); + void warning(const ::Ice::LocalException&) const; + + ::Ice::ObjectAdapterPtr _adapter; + TransceiverPtr _transceiver; + EndpointPtr _endpoint; + ThreadPoolPtr _threadPool; + int _responseCount; + State _state; +#ifndef ICE_NO_TRACE + TraceLevelsPtr _traceLevels; + ::Ice::LoggerPtr _logger; +#endif +}; + +class CollectorFactory : public EventHandler, public JTCMutex +{ +public: + + void destroy(); + void hold(); + void activate(); + + EndpointPtr endpoint() const; + bool equivalent(const EndpointPtr&) const; + + // + // Operations from EventHandler + // + virtual bool server() const; + virtual bool readable() const; + virtual void read(Stream&); + virtual void message(Stream&); + virtual void exception(const ::Ice::LocalException&); + virtual void finished(); + +private: + + CollectorFactory(const InstancePtr&, const ::Ice::ObjectAdapterPtr&, + const EndpointPtr&); + virtual ~CollectorFactory(); + friend class ::Ice::ObjectAdapterI; + + enum State + { + StateActive, + StateHolding, + StateClosing, + StateClosed + }; + + void setState(State); + void clearBacklog(); + void warning(const ::Ice::LocalException&) const; + + ::Ice::ObjectAdapterPtr _adapter; + AcceptorPtr _acceptor; + TransceiverPtr _transceiver; + EndpointPtr _endpoint; + ThreadPoolPtr _threadPool; + std::list<CollectorPtr> _collectors; + State _state; +#ifndef ICE_NO_TRACE + TraceLevelsPtr _traceLevels; + ::Ice::LoggerPtr _logger; +#endif +}; + +} + +#endif diff --git a/cpp/src/Ice/CommunicatorI.cpp b/cpp/src/Ice/CommunicatorI.cpp new file mode 100644 index 00000000000..b7a1a324960 --- /dev/null +++ b/cpp/src/Ice/CommunicatorI.cpp @@ -0,0 +1,208 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/CommunicatorI.h> +#include <Ice/PropertiesI.h> +#include <Ice/Instance.h> +#include <Ice/ProxyFactory.h> +#include <Ice/ThreadPool.h> +#include <Ice/ObjectAdapter.h> +#include <Ice/ValueFactoryManager.h> +#include <Ice/ObjectAdapterFactory.h> +#include <Ice/Logger.h> +#include <Ice/Initialize.h> +#include <Ice/LocalException.h> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +void +Ice::CommunicatorI::destroy() +{ + JTCSyncT<JTCRecursiveMutex> sync(*this); + shutdown(); + _instance->destroy(); + _instance = 0; +} + +void +Ice::CommunicatorI::shutdown() +{ + JTCSyncT<JTCRecursiveMutex> sync(*this); + if (!_instance) + { + throw CommunicatorDestroyedException(__FILE__, __LINE__); + } + _instance->objectAdapterFactory()->shutdown(); +} + +void +Ice::CommunicatorI::waitForShutdown() +{ + ThreadPoolPtr threadPool; + + { + JTCSyncT<JTCRecursiveMutex> sync(*this); + if (!_instance) + { + throw CommunicatorDestroyedException(__FILE__, __LINE__); + } + threadPool = _instance->threadPool(); + } + + threadPool->waitUntilServerFinished(); +} + +ObjectPrx +Ice::CommunicatorI::stringToProxy(const string& s) +{ + JTCSyncT<JTCRecursiveMutex> sync(*this); + if (!_instance) + { + throw CommunicatorDestroyedException(__FILE__, __LINE__); + } + return _instance->proxyFactory()->stringToProxy(s); +} + +ObjectAdapterPtr +Ice::CommunicatorI::createObjectAdapter(const string& name) +{ + JTCSyncT<JTCRecursiveMutex> sync(*this); + if (!_instance) + { + throw CommunicatorDestroyedException(__FILE__, __LINE__); + } + string endpts = _instance->properties()->getProperty("ice.adapter." + name + ".endpoints"); + return createObjectAdapterWithEndpoints(name, endpts); +} + +ObjectAdapterPtr +Ice::CommunicatorI::createObjectAdapterWithEndpoints(const string& name, const string& endpts) +{ + JTCSyncT<JTCRecursiveMutex> sync(*this); + if (!_instance) + { + throw CommunicatorDestroyedException(__FILE__, __LINE__); + } + return _instance->objectAdapterFactory() -> createObjectAdapter(name, endpts); +} + +void +Ice::CommunicatorI::installValueFactory(const ValueFactoryPtr& factory, const string& id) +{ + JTCSyncT<JTCRecursiveMutex> sync(*this); + if (!_instance) + { + throw CommunicatorDestroyedException(__FILE__, __LINE__); + } + _instance->valueFactoryManager()->install(factory, id); +} + +PropertiesPtr +Ice::CommunicatorI::getProperties() +{ + JTCSyncT<JTCRecursiveMutex> sync(*this); + if (!_instance) + { + throw CommunicatorDestroyedException(__FILE__, __LINE__); + } + return _instance->properties(); +} + +LoggerPtr +Ice::CommunicatorI::getLogger() +{ + JTCSyncT<JTCRecursiveMutex> sync(*this); + if (!_instance) + { + throw CommunicatorDestroyedException(__FILE__, __LINE__); + } + return _instance->logger(); +} + +void +Ice::CommunicatorI::setLogger(const LoggerPtr& logger) +{ + JTCSyncT<JTCRecursiveMutex> sync(*this); + if (!_instance) + { + throw CommunicatorDestroyedException(__FILE__, __LINE__); + } + _instance->logger(logger); +} + +PicklerPtr +Ice::CommunicatorI::getPickler() +{ + JTCSyncT<JTCRecursiveMutex> sync(*this); + if (!_instance) + { + throw CommunicatorDestroyedException(__FILE__, __LINE__); + } + return _instance->pickler(); +} + +Ice::CommunicatorI::CommunicatorI(const PropertiesPtr& properties) : + _instance(new ::IceInternal::Instance(this, properties)) +{ +} + +Ice::CommunicatorI::~CommunicatorI() +{ + if (_instance) + { + _instance->logger()->warning("communicator object has not been destroyed"); + } +} + +CommunicatorPtr +Ice::initialize(int&, char*[], Int version) +{ +#ifndef ICE_IGNORE_VERSION + if (version != ICE_INT_VERSION) + { + throw VersionMismatchException(__FILE__, __LINE__); + } +#endif + + PropertiesPtr properties; + const char* file = getenv("ICE_CONFIG"); + if (file && *file != '\0') + properties = new PropertiesI(file); + else + properties = new PropertiesI; + return new CommunicatorI(properties); +} + +CommunicatorPtr +Ice::initializeWithProperties(int&, char*[], const PropertiesPtr& properties, Int version) +{ +#ifndef ICE_IGNORE_VERSION + if (version != ICE_INT_VERSION) + { + throw VersionMismatchException(__FILE__, __LINE__); + } +#endif + + return new CommunicatorI(properties); +} + +PropertiesPtr +Ice::createProperties() +{ + return new PropertiesI; +} + +PropertiesPtr +Ice::loadProperties(const std::string& file) +{ + return new PropertiesI(file); +} diff --git a/cpp/src/Ice/CommunicatorI.h b/cpp/src/Ice/CommunicatorI.h new file mode 100644 index 00000000000..bb75f1c6ba4 --- /dev/null +++ b/cpp/src/Ice/CommunicatorI.h @@ -0,0 +1,59 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_COMMUNICATOR_I_H +#define ICE_COMMUNICATOR_I_H + +#include <Ice/InstanceF.h> +#include <Ice/Communicator.h> +#include <Ice/Shared.h> + +namespace Ice +{ + +class CommunicatorI : public Communicator, public JTCRecursiveMutex +{ +public: + + virtual void destroy(); + virtual void shutdown(); + virtual void waitForShutdown(); + + virtual ObjectPrx stringToProxy(const std::string&); + + virtual ObjectAdapterPtr createObjectAdapter(const std::string&); + virtual ObjectAdapterPtr createObjectAdapterWithEndpoints( + const std::string&, const std::string&); + + virtual void installValueFactory(const ValueFactoryPtr&, + const std::string&); + + virtual PropertiesPtr getProperties(); + + virtual LoggerPtr getLogger(); + virtual void setLogger(const LoggerPtr&); + + virtual PicklerPtr getPickler(); + +private: + + CommunicatorI(const PropertiesPtr&); + virtual ~CommunicatorI(); + + friend ICE_API CommunicatorPtr initialize(int&, char*[], Int); + friend ICE_API CommunicatorPtr initializeWithProperties( + int&, char*[], const PropertiesPtr&, Int); + + ::IceInternal::InstancePtr _instance; +}; + +} + +#endif diff --git a/cpp/src/Ice/Connector.cpp b/cpp/src/Ice/Connector.cpp new file mode 100644 index 00000000000..19b9019b0b7 --- /dev/null +++ b/cpp/src/Ice/Connector.cpp @@ -0,0 +1,18 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/Connector.h> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +void IceInternal::incRef(Connector* p) { p->__incRef(); } +void IceInternal::decRef(Connector* p) { p->__decRef(); } diff --git a/cpp/src/Ice/Connector.h b/cpp/src/Ice/Connector.h new file mode 100644 index 00000000000..12c6267567c --- /dev/null +++ b/cpp/src/Ice/Connector.h @@ -0,0 +1,36 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_CONNECTOR_H +#define ICE_CONNECTOR_H + +#include <Ice/ConnectorF.h> +#include <Ice/TransceiverF.h> +#include <Ice/Shared.h> + +namespace IceInternal +{ + +class Connector : public Shared +{ +public: + + virtual TransceiverPtr connect(int) = 0; + virtual std::string toString() const = 0; + +protected: + + Connector() { } + virtual ~Connector() { } +}; + +} + +#endif diff --git a/cpp/src/Ice/ConnectorF.h b/cpp/src/Ice/ConnectorF.h new file mode 100644 index 00000000000..a46df2ce057 --- /dev/null +++ b/cpp/src/Ice/ConnectorF.h @@ -0,0 +1,26 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_CONNECTOR_F_H +#define ICE_CONNECTOR_F_H + +#include <Ice/Handle.h> + +namespace IceInternal +{ + +class Connector; +void incRef(Connector*); +void decRef(Connector*); +typedef IceInternal::Handle<Connector> ConnectorPtr; + +} + +#endif diff --git a/cpp/src/Ice/Emitter.cpp b/cpp/src/Ice/Emitter.cpp new file mode 100644 index 00000000000..efc2fa351c9 --- /dev/null +++ b/cpp/src/Ice/Emitter.cpp @@ -0,0 +1,421 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/Emitter.h> +#include <Ice/Instance.h> +#include <Ice/Logger.h> +#include <Ice/TraceLevels.h> +#include <Ice/TraceUtil.h> +#include <Ice/Transceiver.h> +#include <Ice/Connector.h> +#include <Ice/ThreadPool.h> +#include <Ice/Endpoint.h> +#include <Ice/Outgoing.h> +#include <Ice/LocalException.h> +#include <Ice/Functional.h> +#include <sstream> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +void IceInternal::incRef(Emitter* p) { p->__incRef(); } +void IceInternal::decRef(Emitter* p) { p->__decRef(); } + +void IceInternal::incRef(EmitterFactory* p) { p->__incRef(); } +void IceInternal::decRef(EmitterFactory* p) { p->__decRef(); } + +void +IceInternal::Emitter::destroy() +{ + exception(CommunicatorDestroyedException(__FILE__, __LINE__)); +} + +bool +IceInternal::Emitter::destroyed() const +{ + JTCSyncT<JTCMutex> sync(*this); + return _state >= StateClosing; +} + +void +IceInternal::Emitter::prepareRequest(Outgoing* out) +{ + Stream* os = out->os(); + os->write(bigendian); + os->write(Byte(0)); // Protocol version + os->write(Byte(0)); // Encoding version + os->write(Byte(0)); // Message type = Request + os->write(Int(0)); // Message size (placeholder) + os->write(Int(0)); // Request ID (placeholder) +} + +void +IceInternal::Emitter::sendRequest(Outgoing* out, bool oneway) +{ + JTCSyncT<JTCMutex> sync(*this); + + if (_exception.get()) + { + _exception->raise(); + } + + assert(_state == StateActive); + + Int requestId; + + try + { + Stream* os = out->os(); + os->i = os->b.begin(); + + // + // Fill in the message size and request ID + // + const Byte* p; + Int sz = os->b.size(); + p = reinterpret_cast<Byte*>(&sz); + copy(p, p + sizeof(Int), os->i + 4); + if (!_endpoint->oneway() && !oneway) + { + requestId = _nextRequestId++; + if (requestId == 0) // 0 means oneway + { + requestId = _nextRequestId++; + } + p = reinterpret_cast<Byte*>(&requestId); + copy(p, p + sizeof(Int), os->i + 8); + } + traceRequest("sending request", *os, _logger, _traceLevels); + _transceiver->write(*os, _endpoint->timeout()); + } + catch(const LocalException& ex) + { + setState(StateClosed, ex); + ex.raise(); + } + + // + // Only add to the request map if there was no exception, and if + // the operation is twoway. + // + if (!_endpoint->oneway() && !oneway) + { + _requests.insert(_requests.end(), make_pair(requestId, out)); + } +} + +int +IceInternal::Emitter::timeout() const +{ + return _endpoint->timeout(); +} + +bool +IceInternal::Emitter::server() const +{ + return true; +} + +bool +IceInternal::Emitter::readable() const +{ + return true; +} + +void +IceInternal::Emitter::read(Stream& stream) +{ + _transceiver->read(stream, 0); +} + +void +IceInternal::Emitter::message(Stream& stream) +{ + JTCSyncT<JTCMutex> sync(*this); + + _threadPool->promoteFollower(); + + if (_state != StateActive) + { + return; + } + + try + { + assert(stream.i == stream.b.end()); + stream.i = stream.b.begin() + 3; + Byte messageType; + stream.read(messageType); + stream.i = stream.b.begin() + 8; + + switch (messageType) + { + case 0: // Request + { + traceRequest("received request on the client side\n" + "(invalid, closing connection)", + stream, _logger, _traceLevels); + throw InvalidMessageException(__FILE__, __LINE__); + break; + } + + case 1: // Reply + { + traceReply("received reply", stream, _logger, _traceLevels); + Int requestId; + stream.read(requestId); + map<Int, Outgoing*>::iterator p = _requests.find(requestId); + if (p == _requests.end()) + { + throw UnknownRequestIdException(__FILE__, __LINE__); + } + p->second->finished(stream); + _requests.erase(p); + break; + } + + case 2: // CloseConnection + { + traceHeader("received close connection", + stream, _logger, _traceLevels); + throw CloseConnectionException(__FILE__, __LINE__); + break; + } + + default: + { + traceHeader("received unknown message\n" + "(invalid, closing connection)", + stream, _logger, _traceLevels); + throw UnknownMessageException(__FILE__, __LINE__); + break; + } + } + } + catch(const LocalException& ex) + { + setState(StateClosed, ex); + return; + } +} + +void +IceInternal::Emitter::exception(const LocalException& ex) +{ + JTCSyncT<JTCMutex> sync(*this); + setState(StateClosed, ex); +} + +void +IceInternal::Emitter::finished() +{ + JTCSyncT<JTCMutex> sync(*this); + _transceiver->close(); +} + +IceInternal::Emitter::Emitter(const InstancePtr& instance, + const TransceiverPtr& transceiver, + const EndpointPtr& endpoint) : + EventHandler(instance), + _transceiver(transceiver), + _endpoint(endpoint), + _nextRequestId(1), + _state(StateActive) +{ +#ifndef ICE_NO_TRACE + _traceLevels = _instance->traceLevels(); + _logger = _instance->logger(); +#endif + + if (!_endpoint->oneway()) + { + _threadPool = _instance->threadPool(); + _threadPool->_register(_transceiver->fd(), this); + } +} + +IceInternal::Emitter::~Emitter() +{ + assert(_state == StateClosed); +} + +void +IceInternal::Emitter::setState(State state, const LocalException& ex) +{ + if (_state == state) // Don't switch twice + { + return; + } + + switch (state) + { + case StateActive: + { + return; // Can't switch back to holding state + } + + case StateClosed: + { + if (_threadPool) + _threadPool->unregister(_transceiver->fd()); + else + _transceiver->close(); + break; + } + } + + if (!_exception.get()) + { + _exception = auto_ptr<LocalException>(ex.clone()); + } + + for (std::map< ::Ice::Int, Outgoing*>::iterator p = _requests.begin(); p != _requests.end(); ++p) + { + p->second->finished(*_exception.get()); + } + _requests.clear(); + + _state = state; +} + +EmitterPtr +IceInternal::EmitterFactory::create(const vector<EndpointPtr>& endpoints) +{ + JTCSyncT<JTCMutex> sync(*this); + + if (!_instance) + { + throw CommunicatorDestroyedException(__FILE__, __LINE__); + } + + assert(!endpoints.empty()); + + // + // First reap destroyed emitters + // + std::map<EndpointPtr, EmitterPtr>::iterator p = _emitters.begin(); + while (p != _emitters.end()) + { + if (p -> second -> destroyed()) + { + std::map<EndpointPtr, EmitterPtr>::iterator p2 = p; + ++p; + _emitters.erase(p2); + } + else + { + ++p; + } + } + + // + // Search for existing emitters + // + vector<EndpointPtr>::const_iterator q; + for (q = endpoints.begin(); q != endpoints.end(); ++q) + { + map<EndpointPtr, EmitterPtr>::const_iterator r = _emitters.find(*q); + if (r != _emitters.end()) + { + return r->second; + } + } + + // + // No emitters exist, try to create one + // +#ifndef ICE_NO_TRACE + TraceLevelsPtr traceLevels = _instance->traceLevels(); + LoggerPtr logger = _instance->logger(); +#endif + + EmitterPtr emitter; + auto_ptr<LocalException> exception; + q = endpoints.begin(); + while (q != endpoints.end()) + { + try + { + TransceiverPtr transceiver = (*q)->clientTransceiver(_instance); + if (!transceiver) + { + ConnectorPtr connector = (*q)->connector(_instance); + assert(connector); + transceiver = connector->connect((*q)->timeout()); + assert(transceiver); + } + emitter = new Emitter(_instance, transceiver, *q); + _emitters.insert(make_pair(*q, emitter)); + break; + } + catch (const SocketException& ex) + { + exception = auto_ptr<LocalException>(ex.clone()); + } + catch (const DNSException& ex) + { + exception = auto_ptr<LocalException>(ex.clone()); + } + + ++q; + +#ifndef ICE_NO_TRACE + if (traceLevels->retry >= 2) + { + ostringstream s; + s << "connection to endpoint failed"; + if (q != endpoints.end()) + { + s << ", trying next endpoint\n"; + } + else + { + s << " and no more endpoints to try\n"; + } + s << *exception.get(); + logger->trace(traceLevels->retryCat, s.str()); + } +#endif + } + + if (!emitter) + { + assert(exception.get()); + exception -> raise(); + } + + return emitter; +} + +IceInternal::EmitterFactory::EmitterFactory(const InstancePtr& instance) : + _instance(instance) +{ +} + +IceInternal::EmitterFactory::~EmitterFactory() +{ + assert(!_instance); +} + +void +IceInternal::EmitterFactory::destroy() +{ + JTCSyncT<JTCMutex> sync(*this); + + if (!_instance) + { + return; + } + + for_each(_emitters.begin(), _emitters.end(), secondVoidMemFun<EndpointPtr, Emitter>(&Emitter::destroy)); + _emitters.clear(); + _instance = 0; +} diff --git a/cpp/src/Ice/Emitter.h b/cpp/src/Ice/Emitter.h new file mode 100644 index 00000000000..20b4eb6a357 --- /dev/null +++ b/cpp/src/Ice/Emitter.h @@ -0,0 +1,105 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_EMITTER_H +#define ICE_EMITTER_H + +#include <Ice/EmitterF.h> +#include <Ice/InstanceF.h> +#include <Ice/TransceiverF.h> +#include <Ice/ConnectorF.h> +#include <Ice/ThreadPoolF.h> +#include <Ice/EndpointF.h> +#include <Ice/TraceLevelsF.h> +#include <Ice/LoggerF.h> +#include <Ice/EventHandler.h> +#include <map> + +namespace Ice +{ + +class LocalException; + +} + +namespace IceInternal +{ + +class Outgoing; + +class Emitter : public EventHandler, public JTCMutex +{ +public: + + void destroy(); + bool destroyed() const; + void prepareRequest(Outgoing*); + void sendRequest(Outgoing*, bool); + int timeout() const; + + // + // Operations from EventHandler + // + virtual bool server() const; + virtual bool readable() const; + virtual void read(Stream&); + virtual void message(Stream&); + virtual void exception(const ::Ice::LocalException&); + virtual void finished(); + +private: + + Emitter(const InstancePtr&, const TransceiverPtr&, const EndpointPtr&); + virtual ~Emitter(); + friend class EmitterFactory; + + enum State + { + StateActive, + StateHolding, + StateClosing, + StateClosed + }; + + void setState(State, const ::Ice::LocalException&); + + TransceiverPtr _transceiver; + EndpointPtr _endpoint; + ThreadPoolPtr _threadPool; + ::Ice::Int _nextRequestId; + std::map< ::Ice::Int, Outgoing*> _requests; + std::auto_ptr< ::Ice::LocalException> _exception; + State _state; +#ifndef ICE_NO_TRACE + TraceLevelsPtr _traceLevels; + ::Ice::LoggerPtr _logger; +#endif +}; + +class EmitterFactory : public Shared, public JTCMutex +{ +public: + + EmitterPtr create(const std::vector<EndpointPtr>&); + +private: + + EmitterFactory(const InstancePtr&); + virtual ~EmitterFactory(); + void destroy(); + friend class Instance; + + InstancePtr _instance; + std::map<EndpointPtr, EmitterPtr> _emitters; +}; + +} + +#endif diff --git a/cpp/src/Ice/Endpoint.cpp b/cpp/src/Ice/Endpoint.cpp new file mode 100644 index 00000000000..2038dbdfb14 --- /dev/null +++ b/cpp/src/Ice/Endpoint.cpp @@ -0,0 +1,1112 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/Endpoint.h> +#include <Ice/Network.h> +#include <Ice/TcpAcceptor.h> +#include <Ice/TcpConnector.h> +#include <Ice/TcpTransceiver.h> +#include <Ice/SslAcceptor.h> +#include <Ice/SslConnector.h> +#include <Ice/SslTransceiver.h> +#include <Ice/UdpTransceiver.h> +#include <Ice/Stream.h> +#include <Ice/LocalException.h> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +void IceInternal::incRef(Endpoint* p) { p->__incRef(); } +void IceInternal::decRef(Endpoint* p) { p->__decRef(); } + +EndpointPtr +IceInternal::Endpoint::endpointFromString(const string& str) +{ + const string delim = " \t\n\r"; + + string s(str); + transform(s.begin(), s.end(), s.begin(), tolower); + + string::size_type beg = s.find_first_not_of(delim); + if (beg == string::npos) + { + throw EndpointParseException(__FILE__, __LINE__); + } + + string::size_type end = s.find_first_of(delim, beg); + if (end == string::npos) + { + end = s.length(); + } + + if (s.compare(beg, end - beg, "tcp") == 0) + { + return new TcpEndpoint(s.substr(end)); + } + + if (s.compare(beg, end - beg, "ssl") == 0) + { + return new SslEndpoint(s.substr(end)); + } + + if (s.compare(beg, end - beg, "udp") == 0) + { + return new UdpEndpoint(s.substr(end)); + } + + throw EndpointParseException(__FILE__, __LINE__); +} + +void +IceInternal::Endpoint::streamRead(Stream* s, EndpointPtr& v) +{ + Short type; + s->read(type); + + switch (type) + { + case TcpEndpointType: + { + v = new TcpEndpoint(s); + break; + } + + case SslEndpointType: + { + v = new SslEndpoint(s); + break; + } + + case UdpEndpointType: + { + v = new UdpEndpoint(s); + break; + } + + default: + { + v = new UnknownEndpoint(s); + break; + } + } +} + +bool +IceInternal::Endpoint::regular() const +{ + return !secure() && !datagram(); +} + +IceInternal::UnknownEndpoint::UnknownEndpoint(Stream* s) +{ + s->read(const_cast<vector<Byte>&>(_rawBytes)); +} + +void +IceInternal::UnknownEndpoint::streamWrite(Stream* s) const +{ + s->write(UnknownEndpointType); + s->write(_rawBytes); +} + +Short +IceInternal::UnknownEndpoint::type() const +{ + return UnknownEndpointType; +} + +bool +IceInternal::UnknownEndpoint::oneway() const +{ + return false; +} + +Int +IceInternal::UnknownEndpoint::timeout() const +{ + return -1; +} + +EndpointPtr +IceInternal::UnknownEndpoint::timeout(Int) const +{ + return const_cast<UnknownEndpoint*>(this); +} + +bool +IceInternal::UnknownEndpoint::datagram() const +{ + return false; +} + +bool +IceInternal::UnknownEndpoint::secure() const +{ + return false; +} + +TransceiverPtr +IceInternal::UnknownEndpoint::clientTransceiver(const InstancePtr&) const +{ + return 0; +} + +TransceiverPtr +IceInternal::UnknownEndpoint::serverTransceiver(const InstancePtr&) const +{ + return 0; +} + +ConnectorPtr +IceInternal::UnknownEndpoint::connector(const InstancePtr& instance) const +{ + return 0; +} + +AcceptorPtr +IceInternal::UnknownEndpoint::acceptor(const InstancePtr& instance) const +{ + return 0; +} + +bool +IceInternal::UnknownEndpoint::equivalent(const TransceiverPtr&) const +{ + return false; +} + +bool +IceInternal::UnknownEndpoint::equivalent(const AcceptorPtr&) const +{ + return false; +} + +bool +IceInternal::UnknownEndpoint::operator==(const Endpoint& r) const +{ + return !operator!=(r); +} + +bool +IceInternal::UnknownEndpoint::operator!=(const Endpoint& r) const +{ + const UnknownEndpoint* p = dynamic_cast<const UnknownEndpoint*>(&r); + if (!p) + { + return true; + } + + if (this == p) + { + return false; + } + + if (_rawBytes != p->_rawBytes) + { + return true; + } + + return false; +} + +bool +IceInternal::UnknownEndpoint::operator<(const Endpoint& r) const +{ + const UnknownEndpoint* p = dynamic_cast<const UnknownEndpoint*>(&r); + if (!p) + { + return true; // unknown is "less than" every other protocol + } + + if (this == p) + { + return false; + } + + if (_rawBytes < p->_rawBytes) + { + return true; + } + else if (_rawBytes != p->_rawBytes) + { + return false; + } + + return false; +} + +IceInternal::TcpEndpoint::TcpEndpoint(const string& ho, Int po, Int ti) : + _host(ho), + _port(po), + _timeout(ti) +{ +} + +IceInternal::TcpEndpoint::TcpEndpoint(const string& str) : + _port(10000), + _timeout(-1) +{ + const string delim = " \t\n\r"; + + string s(str); + transform(s.begin(), s.end(), s.begin(), tolower); + + string::size_type beg; + string::size_type end = 0; + + while (true) + { + beg = s.find_first_not_of(delim, end); + if (beg == string::npos) + { + break; + } + + end = s.find_first_of(delim, beg); + if (end == string::npos) + { + end = s.length(); + } + + string option = s.substr(beg, end - beg); + if (option.length() != 2 || option[0] != '-') + { + throw EndpointParseException(__FILE__, __LINE__); + } + + beg = s.find_first_not_of(delim, end); + if (beg == string::npos) + { + throw EndpointParseException(__FILE__, __LINE__); + } + + end = s.find_first_of(delim, beg); + if (end == string::npos) + { + end = s.length(); + } + + string argument = s.substr(beg, end - beg); + + switch (option[1]) + { + case 'h': + { + const_cast<string&>(_host) = argument; + break; + } + + case 'p': + { + const_cast<Int&>(_port) = atoi(argument.c_str()); + break; + } + + case 't': + { + const_cast<Int&>(_timeout) = atoi(argument.c_str()); + break; + } + + default: + { + throw EndpointParseException(__FILE__, __LINE__); + } + } + } + + if (_host.empty()) + { + // TODO: Whether numeric or not should be configurable + const_cast<string&>(_host) = getLocalHost(true); + } +} + +IceInternal::TcpEndpoint::TcpEndpoint(Stream* s) : + _port(0), + _timeout(-1) +{ + s->startReadEncaps(); + s->read(const_cast<string&>(_host)); + s->read(const_cast<Int&>(_port)); + s->read(const_cast<Int&>(_timeout)); + s->endReadEncaps(); +} + +void +IceInternal::TcpEndpoint::streamWrite(Stream* s) const +{ + s->write(TcpEndpointType); + s->startWriteEncaps(); + s->write(_host); + s->write(_port); + s->write(_timeout); + s->endWriteEncaps(); +} + +Short +IceInternal::TcpEndpoint::type() const +{ + return TcpEndpointType; +} + +bool +IceInternal::TcpEndpoint::oneway() const +{ + return false; +} + +Int +IceInternal::TcpEndpoint::timeout() const +{ + return _timeout; +} + +EndpointPtr +IceInternal::TcpEndpoint::timeout(Int timeout) const +{ + if (timeout == _timeout) + { + return const_cast<TcpEndpoint*>(this); + } + else + { + return new TcpEndpoint(_host, _port, timeout); + } +} + +bool +IceInternal::TcpEndpoint::datagram() const +{ + return false; +} + +bool +IceInternal::TcpEndpoint::secure() const +{ + return false; +} + +TransceiverPtr +IceInternal::TcpEndpoint::clientTransceiver(const InstancePtr&) const +{ + return 0; +} + +TransceiverPtr +IceInternal::TcpEndpoint::serverTransceiver(const InstancePtr&) const +{ + return 0; +} + +ConnectorPtr +IceInternal::TcpEndpoint::connector(const InstancePtr& instance) const +{ + return new TcpConnector(instance, _host, _port); +} + +AcceptorPtr +IceInternal::TcpEndpoint::acceptor(const InstancePtr& instance) const +{ + return new TcpAcceptor(instance, _port); +} + +bool +IceInternal::TcpEndpoint::equivalent(const TransceiverPtr&) const +{ + return false; +} + +bool +IceInternal::TcpEndpoint::equivalent(const AcceptorPtr& acceptor) const +{ + const TcpAcceptor* tcpAcceptor = dynamic_cast<const TcpAcceptor*>(acceptor.get()); + if (!tcpAcceptor) + { + return false; + } + return tcpAcceptor->equivalent(_host, _port); +} + +bool +IceInternal::TcpEndpoint::operator==(const Endpoint& r) const +{ + return !operator!=(r); +} + +bool +IceInternal::TcpEndpoint::operator!=(const Endpoint& r) const +{ + const TcpEndpoint* p = dynamic_cast<const TcpEndpoint*>(&r); + if (!p) + { + return true; + } + + if (this == p) + { + return false; + } + + if (_port != p->_port) + { + return true; + } + + struct sockaddr_in laddr; + struct sockaddr_in raddr; + getAddress(_host.c_str(), _port, laddr); + getAddress(p->_host.c_str(), p->_port, raddr); + + if (memcmp(&laddr, &raddr, sizeof(struct sockaddr_in)) != 0) + { + return true; + } + + if (_timeout != p->_timeout) + { + return true; + } + + return false; +} + +bool +IceInternal::TcpEndpoint::operator<(const Endpoint& r) const +{ + const TcpEndpoint* p = dynamic_cast<const TcpEndpoint*>(&r); + if (!p) + { + if (dynamic_cast<const SslEndpoint*>(&r)) + { + return false; // tcp is not "less than" ssl + } + + if (dynamic_cast<const UdpEndpoint*>(&r)) + { + return false; // tcp is not "less than" udp + } + + if (dynamic_cast<const UnknownEndpoint*>(&r)) + { + return false; // tcp is not "less than" unknown + } + + assert(false); + } + + if (this == p) + { + return false; + } + + struct sockaddr_in laddr; + struct sockaddr_in raddr; + getAddress(_host.c_str(), _port, laddr); + getAddress(p->_host.c_str(), p->_port, raddr); + + if (laddr.sin_addr.s_addr < raddr.sin_addr.s_addr) + { + return true; + } + else if (laddr.sin_addr.s_addr != raddr.sin_addr.s_addr) + { + return false; + } + + if (_port < p->_port) + { + return true; + } + else if (_port != p->_port) + { + return false; + } + + if (_timeout < p->_timeout) + { + return true; + } + else if (_timeout != p->_timeout) + { + return false; + } + + return false; +} + +IceInternal::SslEndpoint::SslEndpoint(const string& ho, Int po, Int ti) : + _host(ho), + _port(po), + _timeout(ti) +{ +} + +IceInternal::SslEndpoint::SslEndpoint(const string& str) : + _port(10000), + _timeout(-1) +{ + const string delim = " \t\n\r"; + + string s(str); + transform(s.begin(), s.end(), s.begin(), tolower); + + string::size_type beg; + string::size_type end = 0; + + while (true) + { + beg = s.find_first_not_of(delim, end); + if (beg == string::npos) + { + break; + } + + end = s.find_first_of(delim, beg); + if (end == string::npos) + { + end = s.length(); + } + + string option = s.substr(beg, end - beg); + if (option.length() != 2 || option[0] != '-') + { + throw EndpointParseException(__FILE__, __LINE__); + } + + beg = s.find_first_not_of(delim, end); + if (beg == string::npos) + { + throw EndpointParseException(__FILE__, __LINE__); + } + + end = s.find_first_of(delim, beg); + if (end == string::npos) + { + end = s.length(); + } + + string argument = s.substr(beg, end - beg); + + switch (option[1]) + { + case 'h': + { + const_cast<string&>(_host) = argument; + break; + } + + case 'p': + { + const_cast<Int&>(_port) = atoi(argument.c_str()); + break; + } + + case 't': + { + const_cast<Int&>(_timeout) = atoi(argument.c_str()); + break; + } + + default: + { + throw EndpointParseException(__FILE__, __LINE__); + } + } + } + + if (_host.empty()) + { + // TODO: Whether numeric or not should be configurable + const_cast<string&>(_host) = getLocalHost(true); + } +} + +IceInternal::SslEndpoint::SslEndpoint(Stream* s) : + _port(0), + _timeout(-1) +{ + s->startReadEncaps(); + s->read(const_cast<string&>(_host)); + s->read(const_cast<Int&>(_port)); + s->read(const_cast<Int&>(_timeout)); + s->endReadEncaps(); +} + +void +IceInternal::SslEndpoint::streamWrite(Stream* s) const +{ + s->write(SslEndpointType); + s->startWriteEncaps(); + s->write(_host); + s->write(_port); + s->write(_timeout); + s->endWriteEncaps(); +} + +Short +IceInternal::SslEndpoint::type() const +{ + return SslEndpointType; +} + +bool +IceInternal::SslEndpoint::oneway() const +{ + return false; +} + +Int +IceInternal::SslEndpoint::timeout() const +{ + return _timeout; +} + +EndpointPtr +IceInternal::SslEndpoint::timeout(Int timeout) const +{ + if (timeout == _timeout) + { + return const_cast<SslEndpoint*>(this); + } + else + { + return new SslEndpoint(_host, _port, timeout); + } +} + +bool +IceInternal::SslEndpoint::datagram() const +{ + return false; +} + +bool +IceInternal::SslEndpoint::secure() const +{ + return true; +} + +TransceiverPtr +IceInternal::SslEndpoint::clientTransceiver(const InstancePtr&) const +{ + return 0; +} + +TransceiverPtr +IceInternal::SslEndpoint::serverTransceiver(const InstancePtr&) const +{ + return 0; +} + +ConnectorPtr +IceInternal::SslEndpoint::connector(const InstancePtr& instance) const +{ + return new SslConnector(instance, _host, _port); +} + +AcceptorPtr +IceInternal::SslEndpoint::acceptor(const InstancePtr& instance) const +{ + return new SslAcceptor(instance, _port); +} + +bool +IceInternal::SslEndpoint::equivalent(const TransceiverPtr&) const +{ + return false; +} + +bool +IceInternal::SslEndpoint::equivalent(const AcceptorPtr& acceptor) const +{ + const SslAcceptor* sslAcceptor = dynamic_cast<const SslAcceptor*>(acceptor.get()); + if (!sslAcceptor) + { + return false; + } + return sslAcceptor->equivalent(_host, _port); +} + +bool +IceInternal::SslEndpoint::operator==(const Endpoint& r) const +{ + return !operator!=(r); +} + +bool +IceInternal::SslEndpoint::operator!=(const Endpoint& r) const +{ + const SslEndpoint* p = dynamic_cast<const SslEndpoint*>(&r); + if (!p) + { + return true; + } + + if (this == p) + { + return false; + } + + if (_port != p->_port) + { + return true; + } + + struct sockaddr_in laddr; + struct sockaddr_in raddr; + getAddress(_host.c_str(), _port, laddr); + getAddress(p->_host.c_str(), p->_port, raddr); + + if (memcmp(&laddr, &raddr, sizeof(struct sockaddr_in)) != 0) + { + return true; + } + + if (_timeout != p->_timeout) + { + return true; + } + + return false; +} + +bool +IceInternal::SslEndpoint::operator<(const Endpoint& r) const +{ + const SslEndpoint* p = dynamic_cast<const SslEndpoint*>(&r); + if (!p) + { + if (dynamic_cast<const TcpEndpoint*>(&r)) + { + return true; // ssl is "less than" tcp + } + + if (dynamic_cast<const UdpEndpoint*>(&r)) + { + return false; // ssl is not "less than" udp + } + + if (dynamic_cast<const UnknownEndpoint*>(&r)) + { + return false; // ssl is not "less than" unknown + } + + assert(false); + } + + if (this == p) + { + return false; + } + + struct sockaddr_in laddr; + struct sockaddr_in raddr; + getAddress(_host.c_str(), _port, laddr); + getAddress(p->_host.c_str(), p->_port, raddr); + + if (laddr.sin_addr.s_addr < raddr.sin_addr.s_addr) + { + return true; + } + else if (laddr.sin_addr.s_addr != raddr.sin_addr.s_addr) + { + return false; + } + + if (_port < p->_port) + { + return true; + } + else if (_port != p->_port) + { + return false; + } + + if (_timeout < p->_timeout) + { + return true; + } + else if (_timeout != p->_timeout) + { + return false; + } + + return false; +} + +IceInternal::UdpEndpoint::UdpEndpoint(const string& ho, Int po) : + _host(ho), + _port(po) +{ +} + +IceInternal::UdpEndpoint::UdpEndpoint(const string& str) : + _port(10000) +{ + const string delim = " \t\n\r"; + + string s(str); + transform(s.begin(), s.end(), s.begin(), tolower); + + string::size_type beg; + string::size_type end = 0; + + while (true) + { + beg = s.find_first_not_of(delim, end); + if (beg == string::npos) + { + break; + } + + end = s.find_first_of(delim, beg); + if (end == string::npos) + { + end = s.length(); + } + + string option = s.substr(beg, end - beg); + if (option.length() != 2 || option[0] != '-') + { + throw EndpointParseException(__FILE__, __LINE__); + } + + beg = s.find_first_not_of(delim, end); + if (beg == string::npos) + { + throw EndpointParseException(__FILE__, __LINE__); + } + + end = s.find_first_of(delim, beg); + if (end == string::npos) + { + end = s.length(); + } + + string argument = s.substr(beg, end - beg); + + switch (option[1]) + { + case 'h': + { + const_cast<string&>(_host) = argument; + break; + } + + case 'p': + { + const_cast<Int&>(_port) = atoi(argument.c_str()); + break; + } + + default: + { + throw EndpointParseException(__FILE__, __LINE__); + } + } + } + + if (_host.empty()) + { + // TODO: Whether numeric or not should be configurable + const_cast<string&>(_host) = getLocalHost(true); + } +} + +IceInternal::UdpEndpoint::UdpEndpoint(Stream* s) : + _port(0) +{ + s->startReadEncaps(); + s->read(const_cast<string&>(_host)); + s->read(const_cast<Int&>(_port)); + s->endReadEncaps(); +} + +void +IceInternal::UdpEndpoint::streamWrite(Stream* s) const +{ + s->write(UdpEndpointType); + s->startWriteEncaps(); + s->write(_host); + s->write(_port); + s->endWriteEncaps(); +} + +Short +IceInternal::UdpEndpoint::type() const +{ + return UdpEndpointType; +} + +bool +IceInternal::UdpEndpoint::oneway() const +{ + return true; +} + +Int +IceInternal::UdpEndpoint::timeout() const +{ + return -1; +} + +EndpointPtr +IceInternal::UdpEndpoint::timeout(Int) const +{ + return const_cast<UdpEndpoint*>(this); +} + +bool +IceInternal::UdpEndpoint::datagram() const +{ + return true; +} + +bool +IceInternal::UdpEndpoint::secure() const +{ + return false; +} + +TransceiverPtr +IceInternal::UdpEndpoint::clientTransceiver(const InstancePtr& instance) const +{ + return new UdpTransceiver(instance, _host, _port); +} + +TransceiverPtr +IceInternal::UdpEndpoint::serverTransceiver(const InstancePtr& instance) const +{ + return new UdpTransceiver(instance, _port); +} + +ConnectorPtr +IceInternal::UdpEndpoint::connector(const InstancePtr&) const +{ + return 0; +} + +AcceptorPtr +IceInternal::UdpEndpoint::acceptor(const InstancePtr&) const +{ + return 0; +} + +bool +IceInternal::UdpEndpoint::equivalent(const TransceiverPtr& transceiver) const +{ + const UdpTransceiver* udpTransceiver = dynamic_cast<const UdpTransceiver*>(transceiver.get()); + if (!udpTransceiver) + { + return false; + } + return udpTransceiver->equivalent(_host, _port); +} + +bool +IceInternal::UdpEndpoint::equivalent(const AcceptorPtr&) const +{ + return false; +} + +bool +IceInternal::UdpEndpoint::operator==(const Endpoint& r) const +{ + return !operator!=(r); +} + +bool +IceInternal::UdpEndpoint::operator!=(const Endpoint& r) const +{ + const UdpEndpoint* p = dynamic_cast<const UdpEndpoint*>(&r); + if (!p) + { + return true; + } + + if (this == p) + { + return false; + } + + if (_port != p->_port) + { + return true; + } + + struct sockaddr_in laddr; + struct sockaddr_in raddr; + getAddress(_host.c_str(), _port, laddr); + getAddress(p->_host.c_str(), p->_port, raddr); + + if (memcmp(&laddr, &raddr, sizeof(struct sockaddr_in)) != 0) + { + return true; + } + + return false; +} + +bool +IceInternal::UdpEndpoint::operator<(const Endpoint& r) const +{ + const UdpEndpoint* p = dynamic_cast<const UdpEndpoint*>(&r); + if (!p) + { + if (dynamic_cast<const SslEndpoint*>(&r)) + { + return true; // udp is "less than" ssl + } + + if (dynamic_cast<const TcpEndpoint*>(&r)) + { + return true; // udp is "less than" tcp + } + + if (dynamic_cast<const UnknownEndpoint*>(&r)) + { + return false; // udp is not "less than" unknown + } + + assert(false); + } + + if (this == p) + { + return false; + } + + struct sockaddr_in laddr; + struct sockaddr_in raddr; + getAddress(_host.c_str(), _port, laddr); + getAddress(p->_host.c_str(), p->_port, raddr); + + if (laddr.sin_addr.s_addr < raddr.sin_addr.s_addr) + { + return true; + } + else if (laddr.sin_addr.s_addr != raddr.sin_addr.s_addr) + { + return false; + } + + if (_port < p->_port) + { + return true; + } + else if (_port != p->_port) + { + return false; + } + + return false; +} diff --git a/cpp/src/Ice/Endpoint.h b/cpp/src/Ice/Endpoint.h new file mode 100644 index 00000000000..279b209b76a --- /dev/null +++ b/cpp/src/Ice/Endpoint.h @@ -0,0 +1,261 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_ENDPOINT_H +#define ICE_ENDPOINT_H + +#include <Ice/EndpointF.h> +#include <Ice/InstanceF.h> +#include <Ice/TransceiverF.h> +#include <Ice/ConnectorF.h> +#include <Ice/AcceptorF.h> +#include <Ice/Shared.h> + +namespace IceInternal +{ + +class Stream; + +const ::Ice::Short UnknownEndpointType = 0; +const ::Ice::Short TcpEndpointType = 1; +const ::Ice::Short SslEndpointType = 2; +const ::Ice::Short UdpEndpointType = 3; + +class Endpoint : public Shared +{ +public: + + Endpoint() { } + + // + // Create an endpoint from a string + // + static EndpointPtr endpointFromString(const std::string&); + + // + // Unmarshal an endpoint + // + static void streamRead(Stream*, EndpointPtr&); + + // + // Marshal the endpoint + // + virtual void streamWrite(Stream*) const = 0; + + // + // Return the endpoint type + // + virtual ::Ice::Short type() const = 0; + + // + // Return true if the endpoint only supports oneway operations. + // + virtual bool oneway() const = 0; + + // + // Return the timeout for the endpoint in milliseconds. 0 means + // non-blocking, -1 means no timeout. + // + virtual ::Ice::Int timeout() const = 0; + + // + // Return a new endpoint with a different timeout value, provided + // that timeouts are supported by the endpoint. Otherwise the same + // endpoint is returned. + // + virtual EndpointPtr timeout(::Ice::Int) const = 0; + + // + // Return true if the endpoint is datagram-based. + // + virtual bool datagram() const = 0; + + // + // Return true if the endpoint is secure. + // + virtual bool secure() const = 0; + + // + // Convenience function for STL algorithms: !datagram() && !secure() + // + bool regular() const; + + // + // Return client- and server-side Transceivers for the endpoint, + // or null if a TransceiverPtr can only be created by Acceptors or + // Connectors. + // + virtual TransceiverPtr clientTransceiver(const InstancePtr&) const = 0; + virtual TransceiverPtr serverTransceiver(const InstancePtr&) const = 0; + + // + // Return Acceptors and Connectors for the endpoint, or null if no + // Acceptors and Connectors are available. + // + virtual ConnectorPtr connector(const InstancePtr&) const = 0; + virtual AcceptorPtr acceptor(const InstancePtr&) const = 0; + + // + // Check whether the endpoint is equivalent to a specific + // Transceiver or Acceptor + // + virtual bool equivalent(const TransceiverPtr&) const = 0; + virtual bool equivalent(const AcceptorPtr&) const = 0; + + // + // Compare endpoints for sorting purposes + // + virtual bool operator==(const Endpoint&) const = 0; + virtual bool operator!=(const Endpoint&) const = 0; + virtual bool operator<(const Endpoint&) const = 0; +}; + +class UnknownEndpoint : public Endpoint +{ +public: + + UnknownEndpoint(Stream*); + + virtual void streamWrite(Stream*) const; + virtual ::Ice::Short type() const; + virtual bool oneway() const; + virtual ::Ice::Int timeout() const; + virtual EndpointPtr timeout(::Ice::Int) const; + virtual bool datagram() const; + virtual bool secure() const; + virtual TransceiverPtr clientTransceiver(const InstancePtr&) const; + virtual TransceiverPtr serverTransceiver(const InstancePtr&) const; + virtual ConnectorPtr connector(const InstancePtr&) const; + virtual AcceptorPtr acceptor(const InstancePtr&) const; + virtual bool equivalent(const TransceiverPtr&) const; + virtual bool equivalent(const AcceptorPtr&) const; + + virtual bool operator==(const Endpoint&) const; + virtual bool operator!=(const Endpoint&) const; + virtual bool operator<(const Endpoint&) const; + +private: + + // + // All members are const, because endpoints are immutable. + // + const std::vector< ::Ice::Byte> _rawBytes; +}; + +class TcpEndpoint : public Endpoint +{ +public: + + TcpEndpoint(const std::string&, ::Ice::Int, ::Ice::Int); + TcpEndpoint(const std::string&); + TcpEndpoint(Stream*); + + virtual void streamWrite(Stream*) const; + virtual ::Ice::Short type() const; + virtual bool oneway() const; + virtual ::Ice::Int timeout() const; + virtual EndpointPtr timeout(::Ice::Int) const; + virtual bool datagram() const; + virtual bool secure() const; + virtual TransceiverPtr clientTransceiver(const InstancePtr&) const; + virtual TransceiverPtr serverTransceiver(const InstancePtr&) const; + virtual ConnectorPtr connector(const InstancePtr&) const; + virtual AcceptorPtr acceptor(const InstancePtr&) const; + virtual bool equivalent(const TransceiverPtr&) const; + virtual bool equivalent(const AcceptorPtr&) const; + + virtual bool operator==(const Endpoint&) const; + virtual bool operator!=(const Endpoint&) const; + virtual bool operator<(const Endpoint&) const; + +private: + + // + // All members are const, because endpoints are immutable. + // + const std::string _host; + const ::Ice::Int _port; + const ::Ice::Int _timeout; +}; + +class SslEndpoint : public Endpoint +{ +public: + + SslEndpoint(const std::string&, ::Ice::Int, ::Ice::Int); + SslEndpoint(const std::string&); + SslEndpoint(Stream*); + + virtual void streamWrite(Stream*) const; + virtual ::Ice::Short type() const; + virtual bool oneway() const; + virtual ::Ice::Int timeout() const; + virtual EndpointPtr timeout(::Ice::Int) const; + virtual bool datagram() const; + virtual bool secure() const; + virtual TransceiverPtr clientTransceiver(const InstancePtr&) const; + virtual TransceiverPtr serverTransceiver(const InstancePtr&) const; + virtual ConnectorPtr connector(const InstancePtr&) const; + virtual AcceptorPtr acceptor(const InstancePtr&) const; + virtual bool equivalent(const TransceiverPtr&) const; + virtual bool equivalent(const AcceptorPtr&) const; + + virtual bool operator==(const Endpoint&) const; + virtual bool operator!=(const Endpoint&) const; + virtual bool operator<(const Endpoint&) const; + +private: + + // + // All members are const, because endpoints are immutable. + // + const std::string _host; + const ::Ice::Int _port; + const ::Ice::Int _timeout; +}; + +class UdpEndpoint : public Endpoint +{ +public: + + UdpEndpoint(const std::string&, ::Ice::Int); + UdpEndpoint(const std::string&); + UdpEndpoint(Stream*); + + virtual void streamWrite(Stream*) const; + virtual ::Ice::Short type() const; + virtual bool oneway() const; + virtual ::Ice::Int timeout() const; + virtual EndpointPtr timeout(::Ice::Int) const; + virtual bool datagram() const; + virtual bool secure() const; + virtual TransceiverPtr clientTransceiver(const InstancePtr&) const; + virtual TransceiverPtr serverTransceiver(const InstancePtr&) const; + virtual ConnectorPtr connector(const InstancePtr&) const; + virtual AcceptorPtr acceptor(const InstancePtr&) const; + virtual bool equivalent(const TransceiverPtr&) const; + virtual bool equivalent(const AcceptorPtr&) const; + + virtual bool operator==(const Endpoint&) const; + virtual bool operator!=(const Endpoint&) const; + virtual bool operator<(const Endpoint&) const; + +private: + + // + // All members are const, because endpoints are immutable. + // + const std::string _host; + const ::Ice::Int _port; +}; + +} + +#endif diff --git a/cpp/src/Ice/EndpointF.h b/cpp/src/Ice/EndpointF.h new file mode 100644 index 00000000000..ceaf2f00c20 --- /dev/null +++ b/cpp/src/Ice/EndpointF.h @@ -0,0 +1,26 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_ENDPOINT_F_H +#define ICE_ENDPOINT_F_H + +#include <Ice/Handle.h> + +namespace IceInternal +{ + +class Endpoint; +void incRef(Endpoint*); +void decRef(Endpoint*); +typedef IceInternal::Handle<Endpoint> EndpointPtr; + +} + +#endif diff --git a/cpp/src/Ice/EventHandler.cpp b/cpp/src/Ice/EventHandler.cpp new file mode 100644 index 00000000000..d81de4f3bcc --- /dev/null +++ b/cpp/src/Ice/EventHandler.cpp @@ -0,0 +1,31 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/EventHandler.h> + + +#include <Ice/Instance.h> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +void IceInternal::incRef(EventHandler* p) { p->__incRef(); } +void IceInternal::decRef(EventHandler* p) { p->__decRef(); } + +IceInternal::EventHandler::EventHandler(const InstancePtr& instance) : + _instance(instance), + _stream(instance) +{ +} + +IceInternal::EventHandler::~EventHandler() +{ +} diff --git a/cpp/src/Ice/EventHandler.h b/cpp/src/Ice/EventHandler.h new file mode 100644 index 00000000000..1fea0a0b3a6 --- /dev/null +++ b/cpp/src/Ice/EventHandler.h @@ -0,0 +1,86 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_EVENT_HANDLER_H +#define ICE_EVENT_HANDLER_H + +#include <Ice/EventHandlerF.h> +#include <Ice/InstanceF.h> +#include <Ice/ThreadPoolF.h> +#include <Ice/Shared.h> +#include <Ice/Stream.h> + +namespace Ice +{ + +class LocalException; + +} + +namespace IceInternal +{ + +class EventHandler : public Shared +{ +public: + + // + // Returns true if the event handler belongs to the server-side of + // an application. Client-side otherwise. + // + virtual bool server() const = 0; + + // + // Return true if read() must be called before calling message(). + // + virtual bool readable() const = 0; + + // + // Read data via the event handler. May only be called if + // readable() returns true. + // + virtual void read(Stream&) = 0; + + // + // A complete message has been received. + // + virtual void message(Stream&) = 0; + + // + // Signal exception during reading or unmarshaling. + // + virtual void exception(const ::Ice::LocalException&) = 0; + + // + // Will be called if the event handler is finally + // unregistered. (Calling unregister() does not unregister + // immediately.) + // + virtual void finished() = 0; + +protected: + + EventHandler(const InstancePtr&); + virtual ~EventHandler(); + + InstancePtr _instance; + +private: + + // + // The _stream data member is for use by ThreadPool only + // + Stream _stream; + friend ThreadPool; +}; + +} + +#endif diff --git a/cpp/src/Ice/EventHandlerF.h b/cpp/src/Ice/EventHandlerF.h new file mode 100644 index 00000000000..1a82dc6d437 --- /dev/null +++ b/cpp/src/Ice/EventHandlerF.h @@ -0,0 +1,26 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_EVENT_HANDLER_F_H +#define ICE_EVENT_HANDLER_F_H + +#include <Ice/Handle.h> + +namespace IceInternal +{ + +class EventHandler; +void incRef(EventHandler*); +void decRef(EventHandler*); +typedef IceInternal::Handle<EventHandler> EventHandlerPtr; + +} + +#endif diff --git a/cpp/src/Ice/Incoming.cpp b/cpp/src/Ice/Incoming.cpp new file mode 100644 index 00000000000..292c7b45bfd --- /dev/null +++ b/cpp/src/Ice/Incoming.cpp @@ -0,0 +1,94 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/Incoming.h> +#include <Ice/ObjectAdapter.h> +#include <Ice/Object.h> +#include <Ice/LocalException.h> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +IceInternal::Incoming::Incoming(const InstancePtr& instance, const ObjectAdapterPtr& adapter) : + _adapter(adapter), + _is(instance), + _os(instance) +{ +} + +IceInternal::Incoming::~Incoming() +{ +} + +void +IceInternal::Incoming::invoke(Stream& is) +{ + _is.swap(is); + string identity; + _is.read(identity); + string operation; + _is.read(operation); + + int statusPos = _os.b.size(); + _os.write(Byte(0)); + + ObjectPtr object = _adapter->identityToObject(identity); + + ObjectLocatorPtr locator; + ObjectPtr cookie; + if (object) + { + locator = _adapter->getObjectLocator(); + if (locator) + { + object = locator->locate(_adapter, identity, cookie); + } + } + + if(!object) + { + *(_os.b.begin() + statusPos) = static_cast<Byte>(DispatchObjectNotExist); + return; + } + + try + { + DispatchStatus status = object->__dispatch(*this, operation); + if (status != DispatchOK && status != DispatchException && status != DispatchOperationNotExist) + { + throw UnknownReplyStatusException(__FILE__, __LINE__); + } + + *(_os.b.begin() + statusPos) = static_cast<Byte>(status); + } + catch(const LocationForward& p) + { + *(_os.b.begin() + statusPos) = static_cast<Byte>(DispatchLocationForward); + write(&_os, p._prx); + } + + if (locator) + { + locator->finished(_adapter, identity, object, cookie); + } +} + +Stream* +IceInternal::Incoming::is() +{ + return &_is; +} + +Stream* +IceInternal::Incoming::os() +{ + return &_os; +} diff --git a/cpp/src/Ice/Instance.cpp b/cpp/src/Ice/Instance.cpp new file mode 100644 index 00000000000..08002462d84 --- /dev/null +++ b/cpp/src/Ice/Instance.cpp @@ -0,0 +1,328 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/Instance.h> +#include <Ice/TraceLevels.h> +#include <Ice/ProxyFactory.h> +#include <Ice/ThreadPool.h> +#include <Ice/Emitter.h> +#include <Ice/ValueFactoryManager.h> +#include <Ice/ObjectAdapterFactory.h> +#include <Ice/LocalException.h> +#include <Ice/LoggerI.h> +#include <Ice/PicklerI.h> + +#ifndef WIN32 +# include <csignal> +#endif + +#ifdef WIN32 +# include <sys/timeb.h> +#else +# include <sys/time.h> +#endif + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +JTCMutex* Instance::_globalStateMutex = new JTCMutex; +JTCInitialize* Instance::_globalStateJTC = 0; + +namespace IceInternal +{ + +class GlobalStateMutexDestroyer +{ +public: + + ~GlobalStateMutexDestroyer() + { + delete Instance::_globalStateMutex; + Instance::_globalStateMutex = 0; + } +}; + +static GlobalStateMutexDestroyer destroyer; + +} + +int Instance::_globalStateCounter = 0; + +void IceInternal::incRef(Instance* p) { p->__incRef(); } +void IceInternal::decRef(Instance* p) { p->__decRef(); } + +::Ice::CommunicatorPtr +IceInternal::Instance::communicator() +{ + JTCSyncT<JTCMutex> sync(*this); + return _communicator; +} + +::Ice::PropertiesPtr +IceInternal::Instance::properties() +{ + JTCSyncT<JTCMutex> sync(*this); + return _properties; +} + +::Ice::LoggerPtr +IceInternal::Instance::logger() +{ + JTCSyncT<JTCMutex> sync(*this); + return _logger; +} + +void +IceInternal::Instance::logger(const ::Ice::LoggerPtr& logger) +{ + JTCSyncT<JTCMutex> sync(*this); + _logger = logger; +} + +TraceLevelsPtr +IceInternal::Instance::traceLevels() +{ + JTCSyncT<JTCMutex> sync(*this); + return _traceLevels; +} + +ProxyFactoryPtr +IceInternal::Instance::proxyFactory() +{ + JTCSyncT<JTCMutex> sync(*this); + return _proxyFactory; +} + +ThreadPoolPtr +IceInternal::Instance::threadPool() +{ + JTCSyncT<JTCMutex> sync(*this); + return _threadPool; +} + +EmitterFactoryPtr +IceInternal::Instance::emitterFactory() +{ + JTCSyncT<JTCMutex> sync(*this); + return _emitterFactory; +} + +ValueFactoryManagerPtr +IceInternal::Instance::valueFactoryManager() +{ + JTCSyncT<JTCMutex> sync(*this); + return _valueFactoryManager; +} + +ObjectAdapterFactoryPtr +IceInternal::Instance::objectAdapterFactory() +{ + JTCSyncT<JTCMutex> sync(*this); + return _objectAdapterFactory; +} + +PicklerPtr +IceInternal::Instance::pickler() +{ + JTCSyncT<JTCMutex> sync(*this); + return _pickler; +} + +IceInternal::Instance::Instance(const CommunicatorPtr& communicator, const PropertiesPtr& properties) +{ + if (_globalStateMutex != 0) + { + _globalStateMutex->lock(); + } + + if (++_globalStateCounter == 1) // Only on first call + { +#ifdef WIN32 + WORD version = MAKEWORD(1, 1); + WSADATA data; + if (WSAStartup(version, &data) != 0) + { + if (_globalStateMutex != 0) + _globalStateMutex->unlock(); + throw SocketException(__FILE__, __LINE__); + } +#endif + +#ifndef WIN32 + struct sigaction action; + action.sa_handler = SIG_IGN; + sigemptyset(&action.sa_mask); + action.sa_flags = 0; + sigaction(SIGPIPE, &action, 0); +#endif + +#ifdef WIN32 + struct _timeb tb; + _ftime(&tb); + srand(tb.millitm); +#else + timeval tv; + gettimeofday(&tv, 0); + srand(tv.tv_usec); +#endif + + if (!JTCInitialize::initialized()) + { + _globalStateJTC = new JTCInitialize(); + } + } + + if (_globalStateMutex != 0) + { + _globalStateMutex->unlock(); + } + + try + { + _communicator = communicator; + _properties = properties; + _logger = new LoggerI; + _traceLevels = new TraceLevels(_properties); + _proxyFactory = new ProxyFactory(this); + _threadPool = new ThreadPool(this); + _emitterFactory = new EmitterFactory(this); + _valueFactoryManager = new ValueFactoryManager(); + _objectAdapterFactory = new ObjectAdapterFactory(this); + _pickler = new PicklerI(this); + } + catch(...) + { + destroy(); + throw; + } +} + +IceInternal::Instance::~Instance() +{ + assert(!_communicator); + assert(!_properties); + assert(!_logger); + assert(!_traceLevels); + assert(!_proxyFactory); + assert(!_threadPool); + assert(!_emitterFactory); + assert(!_valueFactoryManager); + assert(!_objectAdapterFactory); + assert(!_pickler); + + if (_globalStateMutex != 0) + { + _globalStateMutex->lock(); + } + + assert(_globalStateCounter > 0); + if (--_globalStateCounter == 0) // Only on last call + { +#ifdef WIN32 + WSACleanup(); +#endif + +#ifndef WIN32 + struct sigaction action; + action.sa_handler = SIG_DFL; + sigemptyset(&action.sa_mask); + action.sa_flags = 0; + sigaction(SIGPIPE, &action, 0); +#endif + + delete _globalStateJTC; + } + + if (_globalStateMutex != 0) + { + _globalStateMutex->unlock(); + } +} + +void +IceInternal::Instance::destroy() +{ + JTCSyncT<JTCMutex> sync(*this); + + // + // Destroy all contained objects. Then set all references to null, + // to avoid cyclic object dependencies. + // + + if(_communicator) + { + // Don't destroy the communicator -- the communicator destroys + // this object, not the other way + _communicator = 0; + } + + if(_properties) + { + // No destroy function defined + // _properties->destroy(); + _properties = 0; + } + + if(_logger) + { + // No destroy function defined + // _logger->destroy(); + _logger = 0; + } + + if(_traceLevels) + { + // No destroy function defined + // _traceLevels->destroy(); + _traceLevels = 0; + } + + if(_proxyFactory) + { + // No destroy function defined + // _proxyFactory->destroy(); + _proxyFactory = 0; + } + + if(_emitterFactory) + { + _emitterFactory->destroy(); + _emitterFactory = 0; + } + + if(_valueFactoryManager) + { + _valueFactoryManager->destroy(); + _valueFactoryManager = 0; + } + + if(_objectAdapterFactory) + { + // No destroy function defined + // _objectAdapterFactory->destroy(); + _objectAdapterFactory = 0; + } + + if(_pickler) + { + // No destroy function defined + // _pickler->destroy(); + _pickler = 0; + } + + if(_threadPool) + { + _threadPool->waitUntilFinished(); + _threadPool->destroy(); + _threadPool->joinWithAllThreads(); + _threadPool = 0; + } +} diff --git a/cpp/src/Ice/Instance.h b/cpp/src/Ice/Instance.h new file mode 100644 index 00000000000..a109edd70cd --- /dev/null +++ b/cpp/src/Ice/Instance.h @@ -0,0 +1,82 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_INSTANCE_H +#define ICE_INSTANCE_H + +#include <Ice/InstanceF.h> +#include <Ice/CommunicatorF.h> +#include <Ice/PropertiesF.h> +#include <Ice/LoggerF.h> +#include <Ice/TraceLevelsF.h> +#include <Ice/ProxyFactoryF.h> +#include <Ice/ThreadPoolF.h> +#include <Ice/EmitterF.h> +#include <Ice/ValueFactoryManagerF.h> +#include <Ice/ObjectAdapterFactoryF.h> +#include <Ice/PicklerF.h> +#include <Ice/Shared.h> + +namespace Ice +{ + +class CommunicatorI; + +} + +namespace IceInternal +{ + +class Instance : public Shared, public JTCMutex +{ +public: + + ::Ice::CommunicatorPtr communicator(); + ::Ice::PropertiesPtr properties(); + ::Ice::LoggerPtr logger(); + void logger(const ::Ice::LoggerPtr&); + TraceLevelsPtr traceLevels(); + ProxyFactoryPtr proxyFactory(); + ThreadPoolPtr threadPool(); + EmitterFactoryPtr emitterFactory(); + ValueFactoryManagerPtr valueFactoryManager(); + ObjectAdapterFactoryPtr objectAdapterFactory(); + ::Ice::PicklerPtr pickler(); + +private: + + Instance(const ::Ice::CommunicatorPtr&, const ::Ice::PropertiesPtr&); + virtual ~Instance(); + void destroy(); + friend class ::Ice::CommunicatorI; + + ::Ice::CommunicatorPtr _communicator; + ::Ice::PropertiesPtr _properties; + ::Ice::LoggerPtr _logger; + TraceLevelsPtr _traceLevels; + ProxyFactoryPtr _proxyFactory; + ThreadPoolPtr _threadPool; + EmitterFactoryPtr _emitterFactory; + ValueFactoryManagerPtr _valueFactoryManager; + ObjectAdapterFactoryPtr _objectAdapterFactory; + ::Ice::PicklerPtr _pickler; + + // + // Global state management + // + friend class GlobalStateMutexDestroyer; + static JTCMutex* _globalStateMutex; + static JTCInitialize* _globalStateJTC; + static int _globalStateCounter; +}; + +} + +#endif diff --git a/cpp/src/Ice/LocalException.cpp b/cpp/src/Ice/LocalException.cpp new file mode 100644 index 00000000000..2a63fa5f75a --- /dev/null +++ b/cpp/src/Ice/LocalException.cpp @@ -0,0 +1,1219 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/LocalException.h> +#include <Ice/Network.h> +#include <sstream> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +Ice::LocalException::LocalException(const char* file, int line) : + _file(file), + _line(line) +{ +} + +Ice::LocalException::~LocalException() +{ +} + +Ice::LocalException::LocalException(const LocalException& ex) +{ + _line = ex._line; + _file = ex._file; +} + +LocalException& +Ice::LocalException::operator=(const LocalException& ex) +{ + if (this != &ex) + { + _line = ex._line; + _file = ex._file; + } + + return *this; +} + +string +Ice::LocalException::toString() const +{ + return debugInfo() + "unknown local exception"; +} + +LocalException* +Ice::LocalException::clone() const +{ + return new LocalException(*this); +} + +void +Ice::LocalException::raise() const +{ + throw *this; +} + +std::string +Ice::LocalException::debugInfo() const +{ + ostringstream s; + s << _file << ':' << _line << ": "; + return s.str(); +} + +ostream& +Ice::operator<<(ostream& out, const LocalException& ex) +{ + string s = ex.toString(); + return out << s; +} + +Ice::UnknownUserException::UnknownUserException(const char* file, int line) : + LocalException(file, line) +{ +} + +Ice::UnknownUserException::UnknownUserException(const UnknownUserException& ex) : + LocalException(ex) +{ +} + +UnknownUserException& +Ice::UnknownUserException::operator=(const UnknownUserException& ex) +{ + LocalException::operator=(ex); + return *this; +} + +string +Ice::UnknownUserException::toString() const +{ + string s = debugInfo() + "unknown user exception"; + return s; +} + +LocalException* +Ice::UnknownUserException::clone() const +{ + return new UnknownUserException(*this); +} + +void +Ice::UnknownUserException::raise() const +{ + throw *this; +} + +Ice::VersionMismatchException::VersionMismatchException(const char* file, int line) : + LocalException(file, line) +{ +} + +Ice::VersionMismatchException::VersionMismatchException(const VersionMismatchException& ex) : + LocalException(ex) +{ +} + +VersionMismatchException& +Ice::VersionMismatchException::operator=(const VersionMismatchException& ex) +{ + LocalException::operator=(ex); + return *this; +} + +string +Ice::VersionMismatchException::toString() const +{ + string s = debugInfo() + "Ice library version mismatch"; + return s; +} + +LocalException* +Ice::VersionMismatchException::clone() const +{ + return new VersionMismatchException(*this); +} + +void +Ice::VersionMismatchException::raise() const +{ + throw *this; +} + +Ice::CommunicatorDestroyedException::CommunicatorDestroyedException(const char* file, int line) : + LocalException(file, line) +{ +} + +Ice::CommunicatorDestroyedException::CommunicatorDestroyedException(const CommunicatorDestroyedException& ex) : + LocalException(ex) +{ +} + +CommunicatorDestroyedException& +Ice::CommunicatorDestroyedException::operator=(const CommunicatorDestroyedException& ex) +{ + LocalException::operator=(ex); + return *this; +} + +string +Ice::CommunicatorDestroyedException::toString() const +{ + string s = debugInfo() + "communicator object destroyed"; + return s; +} + +LocalException* +Ice::CommunicatorDestroyedException::clone() const +{ + return new CommunicatorDestroyedException(*this); +} + +void +Ice::CommunicatorDestroyedException::raise() const +{ + throw *this; +} + +Ice::ObjectAdapterDeactivatedException::ObjectAdapterDeactivatedException(const char* file, int line) : + LocalException(file, line) +{ +} + +Ice::ObjectAdapterDeactivatedException::ObjectAdapterDeactivatedException(const ObjectAdapterDeactivatedException& ex) : + LocalException(ex) +{ +} + +ObjectAdapterDeactivatedException& +Ice::ObjectAdapterDeactivatedException::operator=(const ObjectAdapterDeactivatedException& ex) +{ + LocalException::operator=(ex); + return *this; +} + +string +Ice::ObjectAdapterDeactivatedException::toString() const +{ + string s = debugInfo() + "object adapter deactivated"; + return s; +} + +LocalException* +Ice::ObjectAdapterDeactivatedException::clone() const +{ + return new ObjectAdapterDeactivatedException(*this); +} + +void +Ice::ObjectAdapterDeactivatedException::raise() const +{ + throw *this; +} + +Ice::WrongObjectAdapterException::WrongObjectAdapterException(const char* file, int line) : + LocalException(file, line) +{ +} + +Ice::WrongObjectAdapterException::WrongObjectAdapterException(const WrongObjectAdapterException& ex) : + LocalException(ex) +{ +} + +WrongObjectAdapterException& +Ice::WrongObjectAdapterException::operator=(const WrongObjectAdapterException& ex) +{ + LocalException::operator=(ex); + return *this; +} + +string +Ice::WrongObjectAdapterException::toString() const +{ + string s = debugInfo() + "no suitable endpoint information available"; + return s; +} + +LocalException* +Ice::WrongObjectAdapterException::clone() const +{ + return new WrongObjectAdapterException(*this); +} + +void +Ice::WrongObjectAdapterException::raise() const +{ + throw *this; +} + +Ice::NoEndpointException::NoEndpointException(const char* file, int line) : + LocalException(file, line) +{ +} + +Ice::NoEndpointException::NoEndpointException(const NoEndpointException& ex) : + LocalException(ex) +{ +} + +NoEndpointException& +Ice::NoEndpointException::operator=(const NoEndpointException& ex) +{ + LocalException::operator=(ex); + return *this; +} + +string +Ice::NoEndpointException::toString() const +{ + string s = debugInfo() + "no suitable endpoint information available"; + return s; +} + +LocalException* +Ice::NoEndpointException::clone() const +{ + return new NoEndpointException(*this); +} + +void +Ice::NoEndpointException::raise() const +{ + throw *this; +} + +Ice::EndpointParseException::EndpointParseException(const char* file, int line) : + LocalException(file, line) +{ +} + +Ice::EndpointParseException::EndpointParseException(const EndpointParseException& ex) : + LocalException(ex) +{ +} + +EndpointParseException& +Ice::EndpointParseException::operator=(const EndpointParseException& ex) +{ + LocalException::operator=(ex); + return *this; +} + +string +Ice::EndpointParseException::toString() const +{ + string s = debugInfo() + "error while parsing endpoint"; + return s; +} + +LocalException* +Ice::EndpointParseException::clone() const +{ + return new EndpointParseException(*this); +} + +void +Ice::EndpointParseException::raise() const +{ + throw *this; +} + +Ice::ReferenceParseException::ReferenceParseException(const char* file, int line) : + LocalException(file, line) +{ +} + +Ice::ReferenceParseException::ReferenceParseException(const ReferenceParseException& ex) : + LocalException(ex) +{ +} + +ReferenceParseException& +Ice::ReferenceParseException::operator=(const ReferenceParseException& ex) +{ + LocalException::operator=(ex); + return *this; +} + +string +Ice::ReferenceParseException::toString() const +{ + string s = debugInfo() + "error while parsing reference"; + return s; +} + +LocalException* +Ice::ReferenceParseException::clone() const +{ + return new ReferenceParseException(*this); +} + +void +Ice::ReferenceParseException::raise() const +{ + throw *this; +} + +Ice::ReferenceIdentityException::ReferenceIdentityException(const char* file, int line) : + LocalException(file, line) +{ +} + +Ice::ReferenceIdentityException::ReferenceIdentityException(const ReferenceIdentityException& ex) : + LocalException(ex) +{ +} + +ReferenceIdentityException& +Ice::ReferenceIdentityException::operator=(const ReferenceIdentityException& ex) +{ + LocalException::operator=(ex); + return *this; +} + +string +Ice::ReferenceIdentityException::toString() const +{ + string s = debugInfo() + "reference identity mismatch in location forward"; + return s; +} + +LocalException* +Ice::ReferenceIdentityException::clone() const +{ + return new ReferenceIdentityException(*this); +} + +void +Ice::ReferenceIdentityException::raise() const +{ + throw *this; +} + +Ice::ObjectNotExistException::ObjectNotExistException(const char* file, int line) : + LocalException(file, line) +{ +} + +Ice::ObjectNotExistException::ObjectNotExistException(const ObjectNotExistException& ex) : + LocalException(ex) +{ +} + +ObjectNotExistException& +Ice::ObjectNotExistException::operator=(const ObjectNotExistException& ex) +{ + LocalException::operator=(ex); + return *this; +} + +string +Ice::ObjectNotExistException::toString() const +{ + string s = debugInfo() + "object does not exist"; + return s; +} + +LocalException* +Ice::ObjectNotExistException::clone() const +{ + return new ObjectNotExistException(*this); +} + +void +Ice::ObjectNotExistException::raise() const +{ + throw *this; +} + +Ice::OperationNotExistException::OperationNotExistException(const char* file, int line) : + LocalException(file, line) +{ +} + +Ice::OperationNotExistException::OperationNotExistException(const OperationNotExistException& ex) : + LocalException(ex) +{ +} + +OperationNotExistException& +Ice::OperationNotExistException::operator=(const OperationNotExistException& ex) +{ + LocalException::operator=(ex); + return *this; +} + +string +Ice::OperationNotExistException::toString() const +{ + string s = debugInfo() + "operation does not exist"; + return s; +} + +LocalException* +Ice::OperationNotExistException::clone() const +{ + return new OperationNotExistException(*this); +} + +void +Ice::OperationNotExistException::raise() const +{ + throw *this; +} + +Ice::NoFactoryException::NoFactoryException(const char* file, int line) : + LocalException(file, line) +{ +} + +Ice::NoFactoryException::NoFactoryException(const NoFactoryException& ex) : + LocalException(ex) +{ +} + +NoFactoryException& +Ice::NoFactoryException::operator=(const NoFactoryException& ex) +{ + LocalException::operator=(ex); + return *this; +} + +string +Ice::NoFactoryException::toString() const +{ + string s = debugInfo() + "no factory installed for class with operations"; + return s; +} + +LocalException* +Ice::NoFactoryException::clone() const +{ + return new NoFactoryException(*this); +} + +void +Ice::NoFactoryException::raise() const +{ + throw *this; +} + +Ice::SystemException::SystemException(const char* file, int line) : + LocalException(file, line) +{ +#ifdef WIN32 + _error = WSAGetLastError(); +#else + _error = errno; +#endif +} + +Ice::SystemException::SystemException(const SystemException& ex) : + LocalException(ex) +{ + _error = ex._error; +} + +SystemException& +Ice::SystemException::operator=(const SystemException& ex) +{ + LocalException::operator=(ex); + + if (this != &ex) + _error = ex._error; + + return *this; +} + +string +Ice::SystemException::toString() const +{ + string s = debugInfo() + "system exception: "; + s += errorToString(_error); + return s; +} + +LocalException* +Ice::SystemException::clone() const +{ + return new SystemException(*this); +} + +void +Ice::SystemException::raise() const +{ + throw *this; +} + +Ice::SocketException::SocketException(const char* file, int line) : + SystemException(file, line) +{ +} + +Ice::SocketException::SocketException(const SocketException& ex) : + SystemException(ex) +{ +} + +SocketException& +Ice::SocketException::operator=(const SocketException& ex) +{ + SystemException::operator=(ex); + return *this; +} + +string +Ice::SocketException::toString() const +{ + string s = debugInfo() + "socket exception: "; + s += errorToString(_error); + return s; +} + +LocalException* +Ice::SocketException::clone() const +{ + return new SocketException(*this); +} + +void +Ice::SocketException::raise() const +{ + throw *this; +} + +Ice::TimeoutException::TimeoutException(const char* file, int line) : + SocketException(file, line) +{ +} + +Ice::TimeoutException::TimeoutException(const TimeoutException& ex) : + SocketException(ex) +{ +} + +TimeoutException& +Ice::TimeoutException::operator=(const TimeoutException& ex) +{ + SocketException::operator=(ex); + return *this; +} + +string +Ice::TimeoutException::toString() const +{ + return debugInfo() + "timeout while sending or receiving data"; +} + +LocalException* +Ice::TimeoutException::clone() const +{ + return new TimeoutException(*this); +} + +void +Ice::TimeoutException::raise() const +{ + throw *this; +} + +Ice::ConnectTimeoutException::ConnectTimeoutException(const char* file, int line) : + TimeoutException(file, line) +{ +} + +Ice::ConnectTimeoutException::ConnectTimeoutException(const ConnectTimeoutException& ex) : + TimeoutException(ex) +{ +} + +ConnectTimeoutException& +Ice::ConnectTimeoutException::operator=(const ConnectTimeoutException& ex) +{ + TimeoutException::operator=(ex); + return *this; +} + +string +Ice::ConnectTimeoutException::toString() const +{ + return debugInfo() + "timeout while establishing a connection"; +} + +LocalException* +Ice::ConnectTimeoutException::clone() const +{ + return new ConnectTimeoutException(*this); +} + +void +Ice::ConnectTimeoutException::raise() const +{ + throw *this; +} + +Ice::ConnectFailedException::ConnectFailedException(const char* file, int line) : + SocketException(file, line) +{ +} + +Ice::ConnectFailedException::ConnectFailedException(const ConnectFailedException& ex) : + SocketException(ex) +{ +} + +ConnectFailedException& +Ice::ConnectFailedException::operator=(const ConnectFailedException& ex) +{ + SocketException::operator=(ex); + return *this; +} + +string +Ice::ConnectFailedException::toString() const +{ + string s = debugInfo() + "connect failed: "; + s += errorToString(_error); + return s; +} + +LocalException* +Ice::ConnectFailedException::clone() const +{ + return new ConnectFailedException(*this); +} + +void +Ice::ConnectFailedException::raise() const +{ + throw *this; +} + +Ice::ConnectionLostException::ConnectionLostException(const char* file, int line) : + SocketException(file, line) +{ +} + +Ice::ConnectionLostException::ConnectionLostException(const ConnectionLostException& ex) : + SocketException(ex) +{ +} + +ConnectionLostException& +Ice::ConnectionLostException::operator=(const ConnectionLostException& ex) +{ + SocketException::operator=(ex); + return *this; +} + +string +Ice::ConnectionLostException::toString() const +{ + string s = debugInfo() + "connection lost: "; + if (_error == 0) + s += "recv() returned zero"; + else + s += errorToString(_error); + return s; +} + +LocalException* +Ice::ConnectionLostException::clone() const +{ + return new ConnectionLostException(*this); +} + +void +Ice::ConnectionLostException::raise() const +{ + throw *this; +} + +Ice::DNSException::DNSException(const char* file, int line) : + SystemException(file, line) +{ +#ifndef WIN32 + _error = h_errno; +#endif +} + +Ice::DNSException::DNSException(const DNSException& ex) : + SystemException(ex) +{ +} + +DNSException& +Ice::DNSException::operator=(const DNSException& ex) +{ + SystemException::operator=(ex); + return *this; +} + +string +Ice::DNSException::toString() const +{ + string s = debugInfo() + "DNS error: "; + s += errorToStringDNS(_error); + return s; +} + +LocalException* +Ice::DNSException::clone() const +{ + return new DNSException(*this); +} + +void +Ice::DNSException::raise() const +{ + throw *this; +} + +Ice::ProtocolException::ProtocolException(const char* file, int line) : + LocalException(file, line) +{ +} + +Ice::ProtocolException::ProtocolException(const ProtocolException& ex) : + LocalException(ex) +{ +} + +ProtocolException& +Ice::ProtocolException::operator=(const ProtocolException& ex) +{ + LocalException::operator=(ex); + return *this; +} + +Ice::UnmarshalOutOfBoundsException::UnmarshalOutOfBoundsException(const char* file, int line) : + ProtocolException(file, line) +{ +} + +Ice::UnmarshalOutOfBoundsException::UnmarshalOutOfBoundsException(const UnmarshalOutOfBoundsException& ex) : + ProtocolException(ex) +{ +} + +UnmarshalOutOfBoundsException& +Ice::UnmarshalOutOfBoundsException::operator=(const UnmarshalOutOfBoundsException& ex) +{ + ProtocolException::operator=(ex); + return *this; +} + +string +Ice::UnmarshalOutOfBoundsException::toString() const +{ + return debugInfo() + "protocol error: out of bounds during unmarshaling"; +} + +LocalException* +Ice::UnmarshalOutOfBoundsException::clone() const +{ + return new UnmarshalOutOfBoundsException(*this); +} + +void +Ice::UnmarshalOutOfBoundsException::raise() const +{ + throw *this; +} + +Ice::ValueUnmarshalException::ValueUnmarshalException(const char* file, int line) : + ProtocolException(file, line) +{ +} + +Ice::ValueUnmarshalException::ValueUnmarshalException(const ValueUnmarshalException& ex) : + ProtocolException(ex) +{ +} + +ValueUnmarshalException& +Ice::ValueUnmarshalException::operator=(const ValueUnmarshalException& ex) +{ + ProtocolException::operator=(ex); + return *this; +} + +string +Ice::ValueUnmarshalException::toString() const +{ + return debugInfo() + "protocol error: value type does not match signature"; +} + +LocalException* +Ice::ValueUnmarshalException::clone() const +{ + return new ValueUnmarshalException(*this); +} + +void +Ice::ValueUnmarshalException::raise() const +{ + throw *this; +} + +Ice::StringEncodingException::StringEncodingException(const char* file, int line) : + ProtocolException(file, line) +{ +} + +Ice::StringEncodingException::StringEncodingException(const StringEncodingException& ex) : + ProtocolException(ex) +{ +} + +StringEncodingException& +Ice::StringEncodingException::operator=(const StringEncodingException& ex) +{ + ProtocolException::operator=(ex); + return *this; +} + +string +Ice::StringEncodingException::toString() const +{ + return debugInfo() + "protocol error: string encoding error"; +} + +LocalException* +Ice::StringEncodingException::clone() const +{ + return new StringEncodingException(*this); +} + +void +Ice::StringEncodingException::raise() const +{ + throw *this; +} + +Ice::MemoryLimitException::MemoryLimitException(const char* file, int line) : + ProtocolException(file, line) +{ +} + +Ice::MemoryLimitException::MemoryLimitException(const MemoryLimitException& ex) : + ProtocolException(ex) +{ +} + +MemoryLimitException& +Ice::MemoryLimitException::operator=(const MemoryLimitException& ex) +{ + ProtocolException::operator=(ex); + return *this; +} + +string +Ice::MemoryLimitException::toString() const +{ + return debugInfo() + "protocol error: memory limit exceeded"; +} + +LocalException* +Ice::MemoryLimitException::clone() const +{ + return new MemoryLimitException(*this); +} + +void +Ice::MemoryLimitException::raise() const +{ + throw *this; +} + +Ice::EncapsulationException::EncapsulationException(const char* file, int line) : + ProtocolException(file, line) +{ +} + +Ice::EncapsulationException::EncapsulationException(const EncapsulationException& ex) : + ProtocolException(ex) +{ +} + +EncapsulationException& +Ice::EncapsulationException::operator=(const EncapsulationException& ex) +{ + ProtocolException::operator=(ex); + return *this; +} + +string +Ice::EncapsulationException::toString() const +{ + return debugInfo() + "protocol error: illegal encapsulation"; +} + +LocalException* +Ice::EncapsulationException::clone() const +{ + return new EncapsulationException(*this); +} + +void +Ice::EncapsulationException::raise() const +{ + throw *this; +} + +Ice::UnsupportedProtocolException::UnsupportedProtocolException(const char* file, int line) : + ProtocolException(file, line) +{ +} + +Ice::UnsupportedProtocolException::UnsupportedProtocolException(const UnsupportedProtocolException& ex) : + ProtocolException(ex) +{ +} + +UnsupportedProtocolException& +Ice::UnsupportedProtocolException::operator=(const UnsupportedProtocolException& ex) +{ + ProtocolException::operator=(ex); + return *this; +} + +string +Ice::UnsupportedProtocolException::toString() const +{ + return debugInfo() + "protocol error: unsupported protocol version"; +} + +LocalException* +Ice::UnsupportedProtocolException::clone() const +{ + return new UnsupportedProtocolException(*this); +} + +void +Ice::UnsupportedProtocolException::raise() const +{ + throw *this; +} + +Ice::UnsupportedEncodingException::UnsupportedEncodingException(const char* file, int line) : + ProtocolException(file, line) +{ +} + +Ice::UnsupportedEncodingException::UnsupportedEncodingException(const UnsupportedEncodingException& ex) : + ProtocolException(ex) +{ +} + +UnsupportedEncodingException& +Ice::UnsupportedEncodingException::operator=(const UnsupportedEncodingException& ex) +{ + ProtocolException::operator=(ex); + return *this; +} + +string +Ice::UnsupportedEncodingException::toString() const +{ + return debugInfo() + "protocol error: unsupported encoding version"; +} + +LocalException* +Ice::UnsupportedEncodingException::clone() const +{ + return new UnsupportedEncodingException(*this); +} + +void +Ice::UnsupportedEncodingException::raise() const +{ + throw *this; +} + +Ice::InvalidMessageException::InvalidMessageException(const char* file, int line) : + ProtocolException(file, line) +{ +} + +Ice::InvalidMessageException::InvalidMessageException(const InvalidMessageException& ex) : + ProtocolException(ex) +{ +} + +InvalidMessageException& +Ice::InvalidMessageException::operator=(const InvalidMessageException& ex) +{ + ProtocolException::operator=(ex); + return *this; +} + +string +Ice::InvalidMessageException::toString() const +{ + return debugInfo() + "protocol error: invalid message type"; +} + +LocalException* +Ice::InvalidMessageException::clone() const +{ + return new InvalidMessageException(*this); +} + +void +Ice::InvalidMessageException::raise() const +{ + throw *this; +} + +Ice::UnknownMessageException::UnknownMessageException(const char* file, int line) : + ProtocolException(file, line) +{ +} + +Ice::UnknownMessageException::UnknownMessageException(const UnknownMessageException& ex) : + ProtocolException(ex) +{ +} + +UnknownMessageException& +Ice::UnknownMessageException::operator=(const UnknownMessageException& ex) +{ + ProtocolException::operator=(ex); + return *this; +} + +string +Ice::UnknownMessageException::toString() const +{ + return debugInfo() + "protocol error: unknown message type"; +} + +LocalException* +Ice::UnknownMessageException::clone() const +{ + return new UnknownMessageException(*this); +} + +void +Ice::UnknownMessageException::raise() const +{ + throw *this; +} + +Ice::UnknownRequestIdException::UnknownRequestIdException(const char* file, int line) : + ProtocolException(file, line) +{ +} + +Ice::UnknownRequestIdException::UnknownRequestIdException(const UnknownRequestIdException& ex) : + ProtocolException(ex) +{ +} + +UnknownRequestIdException& +Ice::UnknownRequestIdException::operator=(const UnknownRequestIdException& ex) +{ + ProtocolException::operator=(ex); + return *this; +} + +string +Ice::UnknownRequestIdException::toString() const +{ + return debugInfo() + "protocol error: unknown request id"; +} + +LocalException* +Ice::UnknownRequestIdException::clone() const +{ + return new UnknownRequestIdException(*this); +} + +void +Ice::UnknownRequestIdException::raise() const +{ + throw *this; +} + +Ice::UnknownReplyStatusException::UnknownReplyStatusException(const char* file, int line) : + ProtocolException(file, line) +{ +} + +Ice::UnknownReplyStatusException::UnknownReplyStatusException(const UnknownReplyStatusException& ex) : + ProtocolException(ex) +{ +} + +UnknownReplyStatusException& +Ice::UnknownReplyStatusException::operator=(const UnknownReplyStatusException& ex) +{ + ProtocolException::operator=(ex); + return *this; +} + +string +Ice::UnknownReplyStatusException::toString() const +{ + return debugInfo() + "protocol error: unknown reply status"; +} + +LocalException* +Ice::UnknownReplyStatusException::clone() const +{ + return new UnknownReplyStatusException(*this); +} + +void +Ice::UnknownReplyStatusException::raise() const +{ + throw *this; +} + +Ice::CloseConnectionException::CloseConnectionException(const char* file, int line) : + ProtocolException(file, line) +{ +} + +Ice::CloseConnectionException::CloseConnectionException(const CloseConnectionException& ex) : + ProtocolException(ex) +{ +} + +CloseConnectionException& +Ice::CloseConnectionException::operator=(const CloseConnectionException& ex) +{ + ProtocolException::operator=(ex); + return *this; +} + +string +Ice::CloseConnectionException::toString() const +{ + return debugInfo() + "protocol error: connection closed by server"; +} + +LocalException* +Ice::CloseConnectionException::clone() const +{ + return new CloseConnectionException(*this); +} + +void +Ice::CloseConnectionException::raise() const +{ + throw *this; +} + diff --git a/cpp/src/Ice/LocalObject.cpp b/cpp/src/Ice/LocalObject.cpp new file mode 100644 index 00000000000..56cce93813f --- /dev/null +++ b/cpp/src/Ice/LocalObject.cpp @@ -0,0 +1,52 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/LocalObject.h> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +void IceInternal::incRef(LocalObject* p) { p->__incRef(); } +void IceInternal::decRef(LocalObject* p) { p->__decRef(); } + +Ice::LocalObjectPtrE::LocalObjectPtrE(const LocalObjectPtrE& p) : + _ptr(p._ptr) +{ +} + +Ice::LocalObjectPtrE::LocalObjectPtrE(const LocalObjectPtr& p) : + _ptr(p) +{ +} + +Ice::LocalObjectPtrE::operator LocalObjectPtr() const +{ + return LocalObjectPtr(dynamic_cast<LocalObject*>(_ptr.get())); +} + +::Ice::LocalObject* +Ice::LocalObjectPtrE::operator->() const +{ + return _ptr.get(); +} + +Ice::LocalObjectPtrE::operator bool() const +{ + return _ptr.get() ? true : false; +} + +Ice::LocalObject::LocalObject() +{ +} + +Ice::LocalObject::~LocalObject() +{ +} diff --git a/cpp/src/Ice/LoggerI.cpp b/cpp/src/Ice/LoggerI.cpp new file mode 100644 index 00000000000..94fe46eabd5 --- /dev/null +++ b/cpp/src/Ice/LoggerI.cpp @@ -0,0 +1,43 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/LoggerI.h> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +void +Ice::LoggerI::trace(const string& category, const string& message) +{ + JTCSyncT<JTCMutex> sync(*this); + string s = "[ " + category + ": " + message + " ]"; + string::size_type idx = 0; + while ((idx = s.find("\n", idx)) != string::npos) + { + s.insert(idx + 1, " "); + ++idx; + } + cerr << s << endl; +} + +void +Ice::LoggerI::warning(const string& message) +{ + JTCSyncT<JTCMutex> sync(*this); + cerr << "warning: " << message << endl; +} + +void +Ice::LoggerI::error(const string& message) +{ + JTCSyncT<JTCMutex> sync(*this); + cerr << "error: " << message << endl; +} diff --git a/cpp/src/Ice/LoggerI.h b/cpp/src/Ice/LoggerI.h new file mode 100644 index 00000000000..dfc41b82e90 --- /dev/null +++ b/cpp/src/Ice/LoggerI.h @@ -0,0 +1,30 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_LOGGER_I_H +#define ICE_LOGGER_I_H + +#include <Ice/Logger.h> + +namespace Ice +{ + +class LoggerI : public Logger, public JTCMutex +{ +public: + + virtual void trace(const std::string&, const std::string&); + virtual void warning(const std::string&); + virtual void error(const std::string&); +}; + +} + +#endif diff --git a/cpp/src/Ice/Makefile b/cpp/src/Ice/Makefile new file mode 100644 index 00000000000..f1e737873e6 --- /dev/null +++ b/cpp/src/Ice/Makefile @@ -0,0 +1,184 @@ +# ********************************************************************** +# +# Copyright (c) 2001 +# MutableRealms, Inc. +# Huntsville, AL, USA +# +# All Rights Reserved +# +# ********************************************************************** + +top_srcdir = ../.. + +BASE = libIce.so +VERSIONED_BASE = $(BASE).$(VERSION) + +NAME = $(top_srcdir)/lib/$(BASE) +VERSIONED_NAME = $(top_srcdir)/lib/$(VERSIONED_BASE) + +TARGETS = $(NAME) $(VERSIONED_NAME) + +OBJS = Shared.o \ + Stream.o \ + LocalException.o \ + Pickler.o \ + PicklerI.o \ + Properties.o \ + PropertiesI.o \ + Logger.o \ + LoggerI.o \ + TraceLevels.o \ + TraceUtil.o \ + Instance.o \ + Communicator.o \ + CommunicatorI.o \ + ObjectAdapter.o \ + ObjectAdapterI.o \ + ObjectAdapterFactory.o \ + ValueFactory.o \ + ValueFactoryManager.o \ + Endpoint.o \ + Reference.o \ + LocalObject.o \ + Object.o \ + ProxyFactory.o \ + Proxy.o \ + Outgoing.o \ + Incoming.o \ + Emitter.o \ + Collector.o \ + Network.o \ + ThreadPool.o \ + EventHandler.o \ + Connector.o \ + Acceptor.o \ + Transceiver.o \ + TcpConnector.o \ + TcpAcceptor.o \ + TcpTransceiver.o \ + SslConnector.o \ + SslAcceptor.o \ + SslTransceiver.o \ + UdpTransceiver.o + +SRCS = $(OBJS:.o=.cpp) + +HDIR = $(includedir)/Ice +IDIR = $(slicedir)/Ice +SLICECMD = $(SLICE) --include-dir Ice --dll-export ICE_API -I$(slicedir) + +include $(top_srcdir)/config/Make.rules + +CPPFLAGS := -I.. $(CPPFLAGS) + +$(VERSIONED_NAME): $(OBJS) + rm -f $@ + $(CXX) $(CXXFLAGS) $(LDFLAGS) -shared -o $@ $(OBJS) + +$(NAME): $(VERSIONED_NAME) + rm -f $@ + ln -s $(VERSIONED_BASE) $@ + +$(HDIR)/Communicator.h Communicator.cpp: $(IDIR)/Communicator.ice $(SLICE) + rm -f $(HDIR)/Communicator.h Communicator.cpp + $(SLICECMD) $(IDIR)/Communicator.ice + mv Communicator.h $(HDIR) + +clean:: + rm -f $(HDIR)/Communicator.h Communicator.cpp + +$(HDIR)/CommunicatorF.h: $(IDIR)/CommunicatorF.ice $(SLICE) + rm -f $(HDIR)/CommunicatorF.h CommunicatorF.cpp + $(SLICECMD) $(IDIR)/CommunicatorF.ice + mv CommunicatorF.h $(HDIR) + rm -f CommunicatorF.cpp + +clean:: + rm -f $(HDIR)/CommunicatorF.h + +$(HDIR)/Logger.h Logger.cpp: $(IDIR)/Logger.ice $(SLICE) + rm -f $(HDIR)/Logger.h Logger.cpp + $(SLICECMD) $(IDIR)/Logger.ice + mv Logger.h $(HDIR) + +clean:: + rm -f $(HDIR)/Logger.h Logger.cpp + +$(HDIR)/LoggerF.h: $(IDIR)/LoggerF.ice $(SLICE) + rm -f $(HDIR)/LoggerF.h LoggerF.cpp + $(SLICECMD) $(IDIR)/LoggerF.ice + mv LoggerF.h $(HDIR) + rm -f LoggerF.cpp + +clean:: + rm -f $(HDIR)/LoggerF.h + +$(HDIR)/ObjectAdapter.h ObjectAdapter.cpp: $(IDIR)/ObjectAdapter.ice $(SLICE) + rm -f $(HDIR)/ObjectAdapter.h ObjectAdapter.cpp + $(SLICECMD) $(IDIR)/ObjectAdapter.ice + mv ObjectAdapter.h $(HDIR) + +clean:: + rm -f $(HDIR)/ObjectAdapter.h ObjectAdapter.cpp + +$(HDIR)/ObjectAdapterF.h: $(IDIR)/ObjectAdapterF.ice $(SLICE) + rm -f $(HDIR)/ObjectAdapterF.h ObjectAdapterF.cpp + $(SLICECMD) $(IDIR)/ObjectAdapterF.ice + mv ObjectAdapterF.h $(HDIR) + rm -f ObjectAdapterF.cpp + +clean:: + rm -f $(HDIR)/ObjectAdapterF.h + +$(HDIR)/Pickler.h Pickler.cpp: $(IDIR)/Pickler.ice $(SLICE) + rm -f $(HDIR)/Pickler.h Pickler.cpp + $(SLICECMD) $(IDIR)/Pickler.ice + mv Pickler.h $(HDIR) + +clean:: + rm -f $(HDIR)/Pickler.h Pickler.cpp + +$(HDIR)/PicklerF.h: $(IDIR)/PicklerF.ice $(SLICE) + rm -f $(HDIR)/PicklerF.h PicklerF.cpp + $(SLICECMD) $(IDIR)/PicklerF.ice + mv PicklerF.h $(HDIR) + rm -f PicklerF.cpp + +$(HDIR)/Properties.h Properties.cpp: $(IDIR)/Properties.ice $(SLICE) + rm -f $(HDIR)/Properties.h Properties.cpp + $(SLICECMD) $(IDIR)/Properties.ice + mv Properties.h $(HDIR) + +clean:: + rm -f $(HDIR)/Properties.h Properties.cpp + +clean:: + rm -f $(HDIR)/PicklerF.h + +$(HDIR)/PropertiesF.h: $(IDIR)/PropertiesF.ice $(SLICE) + rm -f $(HDIR)/PropertiesF.h PropertiesF.cpp + $(SLICECMD) $(IDIR)/PropertiesF.ice + mv PropertiesF.h $(HDIR) + rm -f PropertiesF.cpp + +clean:: + rm -f $(HDIR)/PropertiesF.h + +$(HDIR)/ValueFactory.h ValueFactory.cpp: $(IDIR)/ValueFactory.ice $(SLICE) + rm -f $(HDIR)/ValueFactory.h ValueFactory.cpp + $(SLICECMD) $(IDIR)/ValueFactory.ice + mv ValueFactory.h $(HDIR) + +clean:: + rm -f $(HDIR)/ValueFactory.h ValueFactory.cpp + +$(HDIR)/ValueFactoryF.h: $(IDIR)/ValueFactoryF.ice $(SLICE) + rm -f $(HDIR)/ValueFactoryF.h ValueFactoryF.cpp + $(SLICECMD) $(IDIR)/ValueFactoryF.ice + mv ValueFactoryF.h $(HDIR) + rm -f ValueFactoryF.cpp + +clean:: + rm -f $(HDIR)/ValueFactoryF.h + +include .depend diff --git a/cpp/src/Ice/Network.cpp b/cpp/src/Ice/Network.cpp new file mode 100644 index 00000000000..1c74ec036ad --- /dev/null +++ b/cpp/src/Ice/Network.cpp @@ -0,0 +1,902 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/Network.h> +#include <Ice/LocalException.h> +#include <sstream> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +bool +IceInternal::interrupted() +{ +#ifdef WIN32 + int error = WSAGetLastError(); + if (error == WSAEINTR) + return true; +#else + if (errno == EINTR || + errno == EPROTO) + return true; +#endif + else + return false; +} + +bool +IceInternal::acceptInterrupted() +{ + if (interrupted()) + return true; + +#ifdef WIN32 + int error = WSAGetLastError(); + if (error == WSAECONNABORTED || + error == WSAECONNRESET || + error == WSAETIMEDOUT) + return true; +#else + if (errno == ECONNABORTED || + errno == ECONNRESET || + errno == ETIMEDOUT) + return true; +#endif + else + return false; +} + +bool +IceInternal::noBuffers() +{ +#ifdef WIN32 + int error = WSAGetLastError(); + if (error == WSAENOBUFS || + error == WSAEFAULT) + return true; +#else + if (errno == ENOBUFS) + return true; +#endif + else + return false; +} + +bool +IceInternal::wouldBlock() +{ +#ifdef WIN32 + int error = WSAGetLastError(); + if (error == WSAEWOULDBLOCK) + return true; +#else + if (errno == EAGAIN || + errno == EWOULDBLOCK) + return true; +#endif + else + return false; +} + +bool +IceInternal::connectFailed() +{ +#ifdef WIN32 + int error = WSAGetLastError(); + if (error == WSAECONNREFUSED || + error == WSAETIMEDOUT || + error == WSAENETUNREACH || + error == WSAECONNRESET || + error == WSAESHUTDOWN || + error == WSAECONNABORTED) + return true; +#else + if (errno == ECONNREFUSED || + errno == ETIMEDOUT || + errno == ENETUNREACH || + errno == ECONNRESET || + errno == ESHUTDOWN || + errno == ECONNABORTED) + return true; +#endif + else + return false; +} + +bool +IceInternal::connectInProgress() +{ +#ifdef WIN32 + int error = WSAGetLastError(); + if (error == WSAEWOULDBLOCK) + return true; +#else + if (errno == EINPROGRESS) + return true; +#endif + else + return false; +} + +bool +IceInternal::connectionLost() +{ +#ifdef WIN32 + int error = WSAGetLastError(); + if (error == WSAECONNRESET || + error == WSAESHUTDOWN || + error == WSAECONNABORTED) + return true; +#else + if (errno == ECONNRESET || + errno == ESHUTDOWN || + errno == ECONNABORTED) + return true; +#endif + else + return false; +} + +bool +IceInternal::notConnected() +{ +#ifdef WIN32 + int error = WSAGetLastError(); + if (error == WSAENOTCONN) + return true; +#else + if (errno == ENOTCONN) + return true; +#endif + else + return false; +} + +int +IceInternal::createSocket(bool udp) +{ + int fd; + + if (udp) + fd = socket(PF_INET, SOCK_DGRAM, IPPROTO_UDP); + else + fd = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP); + + if (fd == INVALID_SOCKET) + throw SocketException(__FILE__, __LINE__); + + setBlock(fd, false); + + if (!udp) + { + setTcpNoDelay(fd); + setKeepAlive(fd); + } + + return fd; +} + +void +IceInternal::closeSocket(int fd) +{ +#ifdef WIN32 + int error = WSAGetLastError(); + closesocket(fd); + WSASetLastError(error); +#else + int error = errno; + close(fd); + errno = error; +#endif +} + +void +IceInternal::setBlock(int fd, bool block) +{ + if (block) + { +#ifdef WIN32 + unsigned long arg = 0; + ioctlsocket(fd, FIONBIO, &arg); +#else + int flags = fcntl(fd, F_GETFL); + flags &= ~O_NONBLOCK; + fcntl(fd, F_SETFL, flags); +#endif + } + else + { +#ifdef WIN32 + unsigned long arg = 1; + ioctlsocket(fd, FIONBIO, &arg); +#else + int flags = fcntl(fd, F_GETFL); + flags |= O_NONBLOCK; + fcntl(fd, F_SETFL, flags); +#endif + } +} + +void +IceInternal::setTcpNoDelay(int fd) +{ + int flag = 1; + if (setsockopt(fd, IPPROTO_TCP, TCP_NODELAY, (char*)&flag, sizeof(int)) == SOCKET_ERROR) + { + closeSocket(fd); + throw SocketException(__FILE__, __LINE__); + } +} + +void +IceInternal::setKeepAlive(int fd) +{ + int flag = 1; + if (setsockopt(fd, SOL_SOCKET, SO_KEEPALIVE, (char*)&flag, sizeof(int)) == SOCKET_ERROR) + { + closeSocket(fd); + throw SocketException(__FILE__, __LINE__); + } +} + +void +IceInternal::setSendBufferSize(int fd, int sz) +{ + if (setsockopt(fd, SOL_SOCKET, SO_SNDBUF, (char*)&sz, sizeof(int)) == SOCKET_ERROR) + { + closeSocket(fd); + throw SocketException(__FILE__, __LINE__); + } +} + +void +IceInternal::doBind(int fd, struct sockaddr_in& addr) +{ +#ifndef WIN32 + int flag = 1; + if (setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, (char*)&flag, sizeof(int)) == SOCKET_ERROR) + { + closeSocket(fd); + throw SocketException(__FILE__, __LINE__); + } +#endif + + if (bind(fd, reinterpret_cast<struct sockaddr*>(&addr), sizeof(addr)) == SOCKET_ERROR) + { + closeSocket(fd); + throw SocketException(__FILE__, __LINE__); + } + + socklen_t len = sizeof(addr); + int ret = getsockname(fd, reinterpret_cast<struct sockaddr*>(&addr), &len); + assert(ret != SOCKET_ERROR); +} + +void +IceInternal::doListen(int fd, int backlog) +{ +repeatListen: + if (::listen(fd, backlog) == SOCKET_ERROR) + { + if (interrupted()) + goto repeatListen; + + closeSocket(fd); + throw SocketException(__FILE__, __LINE__); + } +} + +void +IceInternal::doConnect(int fd, struct sockaddr_in& addr, int timeout) +{ +#ifdef WIN32 + // + // Set larger send buffer size to avoid performance problems on + // WIN32 + // + setSendBufferSize(fd, 64 * 1024); +#endif + +repeatConnect: + if (::connect(fd, reinterpret_cast<struct sockaddr*>(&addr), sizeof(addr)) == SOCKET_ERROR) + { + if (interrupted()) + goto repeatConnect; + + if (connectInProgress()) + { + repeatSelect: + int ret; + fd_set wFdSet; + FD_ZERO(&wFdSet); + FD_SET(fd, &wFdSet); +#ifdef WIN32 + // + // WIN32 notifies about connection failures + // through the exception filedescriptors + // + fd_set xFdSet; + FD_ZERO(&xFdSet); + FD_SET(fd, &xFdSet); +#endif + if (timeout >= 0) + { + struct timeval tv; + tv.tv_sec = timeout / 1000; + tv.tv_usec = (timeout - tv.tv_sec * 1000) * 1000; +#ifdef WIN32 + ret = ::select(fd + 1, 0, &wFdSet, &xFdSet, &tv); +#else + ret = ::select(fd + 1, 0, &wFdSet, 0, &tv); +#endif + } + else + { +#ifdef WIN32 + ret = ::select(fd + 1, 0, &wFdSet, &xFdSet, 0); +#else + ret = ::select(fd + 1, 0, &wFdSet, 0, 0); +#endif + } + + if (ret == 0) + { + closeSocket(fd); + throw ConnectTimeoutException(__FILE__, __LINE__); + } + else if (ret == SOCKET_ERROR) + { + if (interrupted()) + goto repeatSelect; + + throw SocketException(__FILE__, __LINE__); + } + +#ifdef WIN32 + // + // Strange windows bug: The following call to Sleep() is + // necessary, otherwise no error is reported through + // getsockopt. + // + Sleep(0); +#endif + socklen_t len = sizeof(socklen_t); + int val; + if (getsockopt(fd, SOL_SOCKET, SO_ERROR, reinterpret_cast<char*>(&val), &len) == SOCKET_ERROR) + { + closeSocket(fd); + throw SocketException(__FILE__, __LINE__); + } + + if (val > 0) + { + closeSocket(fd); +#ifdef WIN32 + WSASetLastError(val); +#else + errno = val; +#endif + if (connectFailed()) + throw ConnectFailedException(__FILE__, __LINE__); + else + throw SocketException(__FILE__, __LINE__); + } + + return; + } + + closeSocket(fd); + if (connectFailed()) + throw ConnectFailedException(__FILE__, __LINE__); + else + throw SocketException(__FILE__, __LINE__); + } +} + +int +IceInternal::doAccept(int fd, int timeout) +{ + int ret; + +repeatAccept: + if ((ret = ::accept(fd, 0, 0)) == INVALID_SOCKET) + { + if (acceptInterrupted()) + goto repeatAccept; + + if (wouldBlock()) + { + repeatSelect: + int ret; + fd_set fdSet; + FD_ZERO(&fdSet); + FD_SET(fd, &fdSet); + if (timeout >= 0) + { + struct timeval tv; + tv.tv_sec = timeout / 1000; + tv.tv_usec = (timeout - tv.tv_sec * 1000) * 1000; + ret = ::select(fd + 1, 0, &fdSet, 0, &tv); + } + else + { + ret = ::select(fd + 1, 0, &fdSet, 0, 0); + } + + if (ret == SOCKET_ERROR) + { + if (interrupted()) + goto repeatSelect; + + throw SocketException(__FILE__, __LINE__); + } + + if (ret == 0) + throw TimeoutException(__FILE__, __LINE__); + + goto repeatAccept; + } + + closeSocket(fd); + throw SocketException(__FILE__, __LINE__); + } + + setTcpNoDelay(ret); + setKeepAlive(ret); + +#ifdef WIN32 + // + // Set larger send buffer size to avoid performance problems on + // WIN32 + // + setSendBufferSize(ret, 64 * 1024); +#endif + + return ret; +} + +static JTCMutex getHostByNameMutex; + +void +IceInternal::getAddress(const char* host, int port, struct sockaddr_in& addr) +{ + memset(&addr, 0, sizeof(struct sockaddr_in)); + addr.sin_family = AF_INET; + addr.sin_port = htons(port); + addr.sin_addr.s_addr = inet_addr(host); + + if (addr.sin_addr.s_addr == INADDR_NONE) + { + JTCSyncT<JTCMutex> sync(getHostByNameMutex); + + struct hostent* entry; + int retry = 5; // TODO: Should be configurable + + do + { + entry = gethostbyname(host); + } +#ifdef WIN32 + while (!entry && WSAGetLastError() == WSATRY_AGAIN && --retry >= 0); +#else + while (!entry && h_errno == TRY_AGAIN && --retry >= 0); +#endif + + if (!entry) + throw DNSException(__FILE__, __LINE__); + + memcpy(&addr.sin_addr, entry->h_addr, entry->h_length); + } +} + +void +IceInternal::getLocalAddress(int port, struct sockaddr_in& addr) +{ + char host[1024 + 1]; + if (gethostname(host, 1024) == -1) + throw SystemException(__FILE__, __LINE__); + + memset(&addr, 0, sizeof(struct sockaddr_in)); + addr.sin_family = AF_INET; + addr.sin_port = htons(port); + + { + JTCSyncT<JTCMutex> sync(getHostByNameMutex); + + struct hostent* entry; + int retry = 5; // TODO: Should be configurable + + do + { + entry = gethostbyname(host); + } +#ifdef WIN32 + while (!entry && WSAGetLastError() == WSATRY_AGAIN && --retry >= 0); +#else + while (!entry && h_errno == TRY_AGAIN && --retry >= 0); +#endif + + if (!entry) + throw DNSException(__FILE__, __LINE__); + + memcpy(&addr.sin_addr, entry->h_addr, entry->h_length); + } +} + +string +IceInternal::getLocalHost(bool numeric) +{ + char host[1024 + 1]; + if (gethostname(host, 1024) == -1) + throw SystemException(__FILE__, __LINE__); + + { + JTCSyncT<JTCMutex> sync(getHostByNameMutex); + + struct hostent* entry; + int retry = 5; // TODO: Should be configurable + + do + entry = gethostbyname(host); +#ifdef WIN32 + while (!entry && WSAGetLastError() == WSATRY_AGAIN && --retry >= 0); +#else + while (!entry && h_errno == TRY_AGAIN && --retry >= 0); +#endif + + if (!entry) + throw DNSException(__FILE__, __LINE__); + + if (numeric) + { + struct sockaddr_in addr; + memset(&addr, 0, sizeof(struct sockaddr_in)); + memcpy(&addr.sin_addr, entry->h_addr, entry->h_length); + return string(inet_ntoa(addr.sin_addr)); + } + else + return string(entry->h_name); + } +} + +void +IceInternal::createPipe(int fds[2]) +{ +#ifdef WIN32 + + int fd = createSocket(false); + + struct sockaddr_in addr; + memset(&addr, 0, sizeof(addr)); + addr.sin_family = AF_INET; + addr.sin_port = htons(0); + addr.sin_addr.s_addr = htonl(INADDR_LOOPBACK); + + doBind(fd, addr); + doListen(fd, 1); + + try + { + fds[0] = createSocket(false); + } + catch(...) + { + closeSocket(fd); + throw; + } + + try + { + doConnect(fds[0], addr, -1); + fds[1] = doAccept(fd, -1); + } + catch(...) + { + closeSocket(fd); + closeSocket(fds[0]); + throw; + } + + closeSocket(fd); + +#else + + if (::pipe(fds) != 0) + throw SystemException(__FILE__, __LINE__); + +#endif +} + +#ifdef WIN32 + +const char* +IceInternal::errorToString(int error) +{ + switch (error) + { + case WSAEINTR: + return "WSAEINTR"; + + case WSAEBADF: + return "WSAEBADF"; + + case WSAEACCES: + return "WSAEACCES"; + + case WSAEFAULT: + return "WSAEFAULT"; + + case WSAEINVAL: + return "WSAEINVAL"; + + case WSAEMFILE: + return "WSAEMFILE"; + + case WSAEWOULDBLOCK: + return "WSAEWOULDBLOCK"; + + case WSAEINPROGRESS: + return "WSAEINPROGRESS"; + + case WSAEALREADY: + return "WSAEALREADY"; + + case WSAENOTSOCK: + return "WSAENOTSOCK"; + + case WSAEDESTADDRREQ: + return "WSAEDESTADDRREQ"; + + case WSAEMSGSIZE: + return "WSAEMSGSIZE"; + + case WSAEPROTOTYPE: + return "WSAEPROTOTYPE"; + + case WSAENOPROTOOPT: + return "WSAENOPROTOOPT"; + + case WSAEPROTONOSUPPORT: + return "WSAEPROTONOSUPPORT"; + + case WSAESOCKTNOSUPPORT: + return "WSAESOCKTNOSUPPORT"; + + case WSAEOPNOTSUPP: + return "WSAEOPNOTSUPP"; + + case WSAEPFNOSUPPORT: + return "WSAEPFNOSUPPORT"; + + case WSAEAFNOSUPPORT: + return "WSAEAFNOSUPPORT"; + + case WSAEADDRINUSE: + return "WSAEADDRINUSE"; + + case WSAEADDRNOTAVAIL: + return "WSAEADDRNOTAVAIL"; + + case WSAENETDOWN: + return "WSAENETDOWN"; + + case WSAENETUNREACH: + return "WSAENETUNREACH"; + + case WSAENETRESET: + return "WSAENETRESET"; + + case WSAECONNABORTED: + return "WSAECONNABORTED"; + + case WSAECONNRESET: + return "WSAECONNRESET"; + + case WSAENOBUFS: + return "WSAENOBUFS"; + + case WSAEISCONN: + return "WSAEISCONN"; + + case WSAENOTCONN: + return "WSAENOTCONN"; + + case WSAESHUTDOWN: + return "WSAESHUTDOWN"; + + case WSAETOOMANYREFS: + return "WSAETOOMANYREFS"; + + case WSAETIMEDOUT: + return "WSAETIMEDOUT"; + + case WSAECONNREFUSED: + return "WSAECONNREFUSED"; + + case WSAELOOP: + return "WSAELOOP"; + + case WSAENAMETOOLONG: + return "WSAENAMETOOLONG"; + + case WSAEHOSTDOWN: + return "WSAEHOSTDOWN"; + + case WSAEHOSTUNREACH: + return "WSAEHOSTUNREACH"; + + case WSAENOTEMPTY: + return "WSAENOTEMPTY"; + + case WSAEPROCLIM: + return "WSAEPROCLIM"; + + case WSAEUSERS: + return "WSAEUSERS"; + + case WSAEDQUOT: + return "WSAEDQUOT"; + + case WSAESTALE: + return "WSAESTALE"; + + case WSAEREMOTE: + return "WSAEREMOTE"; + + case WSAEDISCON: + return "WSAEDISCON"; + + case WSASYSNOTREADY: + return "WSASYSNOTREADY"; + + case WSAVERNOTSUPPORTED: + return "WSAVERNOTSUPPORTED"; + + case WSANOTINITIALISED: + return "WSANOTINITIALISED"; + + case WSAHOST_NOT_FOUND: + return "WSAHOST_NOT_FOUND"; + + case WSATRY_AGAIN: + return "WSATRY_AGAIN"; + + case WSANO_RECOVERY: + return "WSANO_RECOVERY"; + + case WSANO_DATA: + return "WSANO_DATA"; + + default: + return "unknown error"; + } +} + +const char* +IceInternal::errorToStringDNS(int error) +{ + return errorToString(error); +} + +#else + +const char* +IceInternal::errorToString(int error) +{ + return strerror(error); +} + +const char* +IceInternal::errorToStringDNS(int error) +{ + switch (error) + { + case NETDB_SUCCESS: + return "no problem"; + + case NETDB_INTERNAL: + return "internal problem"; + + case HOST_NOT_FOUND: + return "no such host is known"; + + case TRY_AGAIN: + return "temporary error, try again"; + + case NO_RECOVERY: + return "unexpected server failure"; + + case NO_DATA: + return "name has no IP address"; + + default: + return "unknown error"; + } +} + +#endif + +const char* +IceInternal::lastErrorToString() +{ +#ifdef WIN32 + return errorToString(WSAGetLastError()); +#else + return errorToString(errno); +#endif +} + +const char* +IceInternal::lastErrorToStringDNS() +{ +#ifdef WIN32 + return errorToStringDNS(WSAGetLastError()); +#else + return errorToStringDNS(h_errno); +#endif +} + +static JTCMutex inetNtoaMutex; + +std::string +IceInternal::fdToString(int fd) +{ + socklen_t localLen = sizeof(struct sockaddr_in); + struct sockaddr_in localAddr; + if (getsockname(fd, reinterpret_cast<struct sockaddr*>(&localAddr), &localLen) == SOCKET_ERROR) + { + closeSocket(fd); + throw SocketException(__FILE__, __LINE__); + } + + bool peerNotConnected = false; + socklen_t remoteLen = sizeof(struct sockaddr_in); + struct sockaddr_in remoteAddr; + if (getpeername(fd, reinterpret_cast<struct sockaddr*>(&remoteAddr), &remoteLen) == SOCKET_ERROR) + { + if (notConnected()) + { + peerNotConnected = true; + } + else + { + closeSocket(fd); + throw SocketException(__FILE__, __LINE__); + } + } + + ostringstream s; + + { + JTCSyncT<JTCMutex> sync(inetNtoaMutex); + + s << "local address = " << inet_ntoa(localAddr.sin_addr) << ':' << ntohs(localAddr.sin_port); + if (peerNotConnected) + { + s << "\nremote address = <not connected>"; + } + else + { + s << "\nremote address = " << inet_ntoa(remoteAddr.sin_addr) << ':' << ntohs(remoteAddr.sin_port); + } + } + + return s.str(); +} + +std::string +IceInternal::addrToString(const struct sockaddr_in& addr) +{ + JTCSyncT<JTCMutex> sync(inetNtoaMutex); + ostringstream s; + s << inet_ntoa(addr.sin_addr) << ':' << ntohs(addr.sin_port); + return s.str(); +} diff --git a/cpp/src/Ice/Network.h b/cpp/src/Ice/Network.h new file mode 100644 index 00000000000..90c64816eab --- /dev/null +++ b/cpp/src/Ice/Network.h @@ -0,0 +1,102 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_NETWORK_H +#define ICE_NETWORK_H + +#include <Ice/Config.h> + +#ifdef WIN32 +# include <winsock.h> +#else +# include <unistd.h> +# include <fcntl.h> +# include <sys/socket.h> +# include <sys/select.h> +# include <netinet/in.h> +# include <netinet/tcp.h> +# include <arpa/inet.h> +# include <netdb.h> +#endif + +#ifdef WIN32 +typedef int socklen_t; +#endif + +#ifndef SOCKET_ERROR +# define SOCKET_ERROR -1 +#endif + +#ifndef INVALID_SOCKET +# define INVALID_SOCKET -1 +#endif + +#ifndef SHUT_RD +# define SHUT_RD 0 +#endif + +#ifndef SHUT_WR +# define SHUT_WR 1 +#endif + +#ifndef SHUT_RDWR +# define SHUT_RDWR 2 +#endif + +#ifndef NETDB_INTERNAL +# define NETDB_INTERNAL -1 +#endif + +#ifndef NETDB_SUCCESS +# define NETDB_SUCCESS 0 +#endif + +namespace IceInternal +{ + +bool interrupted(); +bool acceptInterrupted(); +bool noBuffers(); +bool wouldBlock(); +bool connectFailed(); +bool connectInProgress(); +bool connectionLost(); +bool notConnected(); + +int createSocket(bool); +void closeSocket(int); + +void setBlock(int, bool); +void setTcpNoDelay(int); +void setKeepAlive(int); +void setSendBufferSize(int, int); + +void doBind(int, struct sockaddr_in&); +void doListen(int, int); +void doConnect(int, struct sockaddr_in&, int); +int doAccept(int, int); + +void getAddress(const char*, int, struct sockaddr_in&); +void getLocalAddress(int, struct sockaddr_in&); +std::string getLocalHost(bool); + +void createPipe(int fds[2]); + +const char* errorToString(int); +const char* errorToStringDNS(int); +const char* lastErrorToString(); +const char* lastErrorToStringDNS(); + +std::string fdToString(int); +std::string addrToString(const struct sockaddr_in&); + +} + +#endif diff --git a/cpp/src/Ice/Object.cpp b/cpp/src/Ice/Object.cpp new file mode 100644 index 00000000000..4ed98ae9298 --- /dev/null +++ b/cpp/src/Ice/Object.cpp @@ -0,0 +1,126 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/Object.h> +#include <Ice/Incoming.h> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +void IceInternal::incRef(Object* p) { p->__incRef(); } +void IceInternal::decRef(Object* p) { p->__decRef(); } + +Ice::LocationForward::LocationForward(const LocationForward& p) : + _prx(p._prx) +{ +} + +Ice::LocationForward::LocationForward(const ObjectPrx& p) : + _prx(p) +{ +} + +Ice::ObjectPtrE::ObjectPtrE(const ObjectPtrE& p) : + _ptr(p._ptr) +{ +} + +Ice::ObjectPtrE::ObjectPtrE(const ObjectPtr& p) : + _ptr(p) +{ +} + +Ice::ObjectPtrE::operator ObjectPtr() const +{ + return _ptr; +} + +::Ice::Object* +Ice::ObjectPtrE::operator->() const +{ + return _ptr.get(); +} + +Ice::ObjectPtrE::operator bool() const +{ + return _ptr.get() ? true : false; +} + +Ice::Object::Object() +{ +} + +Ice::Object::~Object() +{ +} + +void +Ice::Object::_throw() +{ + throw ObjectPtrE(this); +} + +bool +Ice::Object::_isA(const string& s) +{ + return s == "::Ice::Object"; +} + +void +Ice::Object::_ping() +{ +} + +DispatchStatus +Ice::Object::____isA(Incoming& __in) +{ + Stream* __is = __in.is(); + Stream* __os = __in.os(); + string s; + __is->read(s); + bool __ret = _isA(s); + __os->write(__ret); + return DispatchOK; +} + +DispatchStatus +Ice::Object::____ping(Incoming&) +{ + _ping(); + return DispatchOK; +} + +string Ice::Object::__names[] = +{ + "_isA" + "_ping" +}; + +DispatchStatus +Ice::Object::__dispatch(::IceInternal::Incoming& in, const string& name) +{ + string* b = __names; + string* e = __names + sizeof(__names) / sizeof(string); + pair<string*, string*> r = equal_range(b, e, name); + if (r.first == r.second) + return DispatchOperationNotExist; + + switch (r.first - __names) + { + case 0: + return ____isA(in); + case 1: + return ____ping(in); + } + + assert(false); + return DispatchOperationNotExist; +} diff --git a/cpp/src/Ice/ObjectAdapterFactory.cpp b/cpp/src/Ice/ObjectAdapterFactory.cpp new file mode 100644 index 00000000000..0df7b32816f --- /dev/null +++ b/cpp/src/Ice/ObjectAdapterFactory.cpp @@ -0,0 +1,69 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/ObjectAdapterFactory.h> +#include <Ice/ObjectAdapterI.h> +#include <Ice/Functional.h> + + +#include <Ice/Instance.h> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +void IceInternal::incRef(ObjectAdapterFactory* p) { p->__incRef(); } +void IceInternal::decRef(ObjectAdapterFactory* p) { p->__decRef(); } + +void +IceInternal::ObjectAdapterFactory::shutdown() +{ + JTCSyncT<JTCMutex> sync(*this); + for_each(_adapters.begin(), _adapters.end(), secondVoidMemFun<string, ObjectAdapter>(&ObjectAdapter::deactivate)); + _adapters.clear(); +} + +ObjectAdapterPtr +IceInternal::ObjectAdapterFactory::createObjectAdapter(const string& name, const string& endpts) +{ + JTCSyncT<JTCMutex> sync(*this); + map<string, ObjectAdapterPtr>::iterator p = _adapters.find(name); + if (p != _adapters.end()) + { + return p->second; + } + + ObjectAdapterPtr adapter = new ObjectAdapterI(_instance, name, endpts); + _adapters.insert(make_pair(name, adapter)); + return adapter; +} + +ObjectPtr +IceInternal::ObjectAdapterFactory::proxyToObject(const ObjectPrx& proxy) +{ + map<string, ObjectAdapterPtr>::iterator p; + for (p = _adapters.begin(); p != _adapters.end(); ++p) + { + try + { + return p->second->proxyToObject(proxy); + } + catch(const WrongObjectAdapterException&) + { + } + } + + return 0; +} + +IceInternal::ObjectAdapterFactory::ObjectAdapterFactory(const InstancePtr& instance) : + _instance(instance) +{ +} diff --git a/cpp/src/Ice/ObjectAdapterFactory.h b/cpp/src/Ice/ObjectAdapterFactory.h new file mode 100644 index 00000000000..d8f9e394ad4 --- /dev/null +++ b/cpp/src/Ice/ObjectAdapterFactory.h @@ -0,0 +1,46 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_OBJECT_ADAPTER_FACTORY_H +#define ICE_OBJECT_ADAPTER_FACTORY_H + +#include <Ice/ObjectAdapterFactoryF.h> +#include <Ice/InstanceF.h> +#include <Ice/ObjectAdapterF.h> +#include <Ice/ProxyF.h> +#include <Ice/ObjectF.h> +#include <Ice/Shared.h> +#include <map> + +namespace IceInternal +{ + +class ObjectAdapterFactory : public Shared, public JTCMutex +{ +public: + + void shutdown(); + ::Ice::ObjectAdapterPtr createObjectAdapter(const std::string&, + const std::string&); + ::Ice::ObjectPtr proxyToObject(const ::Ice::ObjectPrx&); + +private: + + ObjectAdapterFactory(const InstancePtr&); + void destroy(); + friend class Instance; + + InstancePtr _instance; + std::map<std::string, ::Ice::ObjectAdapterPtr> _adapters; +}; + +} + +#endif diff --git a/cpp/src/Ice/ObjectAdapterI.cpp b/cpp/src/Ice/ObjectAdapterI.cpp new file mode 100644 index 00000000000..2a5ecee51ad --- /dev/null +++ b/cpp/src/Ice/ObjectAdapterI.cpp @@ -0,0 +1,324 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/ObjectAdapterI.h> +#include <Ice/Instance.h> +#include <Ice/Proxy.h> +#include <Ice/ProxyFactory.h> +#include <Ice/Reference.h> +#include <Ice/Endpoint.h> +#include <Ice/Collector.h> +#include <Ice/LocalException.h> +#include <Ice/Functional.h> +#include <sstream> + +#ifdef WIN32 +# include <sys/timeb.h> +#else +# include <sys/time.h> +#endif + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +string +Ice::ObjectAdapterI::getName() +{ + return _name; // _name is immutable +} + +CommunicatorPtr +Ice::ObjectAdapterI::getCommunicator() +{ + return _instance->communicator(); // _instance is immutable +} + +void +Ice::ObjectAdapterI::activate() +{ + JTCSyncT<JTCMutex> sync(*this); + + if (_collectorFactories.empty()) + { + throw ObjectAdapterDeactivatedException(__FILE__, __LINE__); + } + + for_each(_collectorFactories.begin(), _collectorFactories.end(), + voidMemFun(& ::IceInternal::CollectorFactory::activate)); +} + +void +Ice::ObjectAdapterI::hold() +{ + JTCSyncT<JTCMutex> sync(*this); + + if (_collectorFactories.empty()) + { + throw ObjectAdapterDeactivatedException(__FILE__, __LINE__); + } + + for_each(_collectorFactories.begin(), _collectorFactories.end(), + voidMemFun(& ::IceInternal::CollectorFactory::hold)); +} + +void +Ice::ObjectAdapterI::deactivate() +{ + JTCSyncT<JTCMutex> sync(*this); + + if (_collectorFactories.empty()) + { + throw ObjectAdapterDeactivatedException(__FILE__, __LINE__); + } + + for_each(_collectorFactories.begin(), _collectorFactories.end(), + voidMemFun(& ::IceInternal::CollectorFactory::destroy)); + _collectorFactories.clear(); + _objects.clear(); +} + +void +Ice::ObjectAdapterI::add(const ObjectPtr& object, const string& identity) +{ + JTCSyncT<JTCMutex> sync(*this); + + if (_collectorFactories.empty()) + { + throw ObjectAdapterDeactivatedException(__FILE__, __LINE__); + } + + _objects.insert(make_pair(identity, object)); +} + +void +Ice::ObjectAdapterI::addTemporary(const ObjectPtr& object) +{ + JTCSyncT<JTCMutex> sync(*this); + + if (_collectorFactories.empty()) + { + throw ObjectAdapterDeactivatedException(__FILE__, __LINE__); + } + + ostringstream s; + +#ifdef WIN32 + struct _timeb tb; + _ftime(&tb); + s << hex << '.' << tb.time << '.' << tb.millitm << '.' << rand(); +#else + timeval tv; + gettimeofday(&tv, 0); + s << hex << '.' << tv.tv_sec << '.' << tv.tv_usec / 1000 << '.' << rand(); +#endif + + _objects.insert(make_pair(s.str(), object)); +} + +void +Ice::ObjectAdapterI::remove(const string& identity) +{ + JTCSyncT<JTCMutex> sync(*this); + + if (_collectorFactories.empty()) + { + throw ObjectAdapterDeactivatedException(__FILE__, __LINE__); + } + + _objects.erase(identity); +} + +void +Ice::ObjectAdapterI::setObjectLocator(const ObjectLocatorPtr& locator) +{ + JTCSyncT<JTCMutex> sync(*this); + _locator = locator; +} + +ObjectLocatorPtr +Ice::ObjectAdapterI::getObjectLocator() +{ + JTCSyncT<JTCMutex> sync(*this); + return _locator; +} + +ObjectPtr +Ice::ObjectAdapterI::identityToObject(const string& identity) +{ + JTCSyncT<JTCMutex> sync(*this); + + map<string, ObjectPtr>::const_iterator p = _objects.find(identity); + if (p == _objects.end()) + { + return 0; + } + + return p->second; +} + +string +Ice::ObjectAdapterI::objectToIdentity(const ObjectPtr& object) +{ + JTCSyncT<JTCMutex> sync(*this); + + if (_collectorFactories.empty()) + { + throw ObjectAdapterDeactivatedException(__FILE__, __LINE__); + } + + map<string, ObjectPtr>::const_iterator p; + for (p = _objects.begin(); p != _objects.end(); ++p) + { + if (object.get() == p->second.get()) + { + return p->first; + } + } + + return string(); +} + +ObjectPtr +Ice::ObjectAdapterI::proxyToObject(const ObjectPrx& proxy) +{ + // + // We must first check whether at least one endpoint contained in + // the proxy matches this object adapter. + // + ReferencePtr ref = proxy->__reference(); + vector<EndpointPtr>::const_iterator p; + for (p = ref->endpoints.begin(); p != ref->endpoints.end(); ++p) + { + vector<CollectorFactoryPtr>::const_iterator q; + for (q = _collectorFactories.begin(); q != _collectorFactories.end(); ++q) + { + if ((*q)->equivalent(*p)) + { + // + // OK, endpoints and object adapter match. Let's find + // the object. + // + return identityToObject(ref->identity); + } + } + } + + throw WrongObjectAdapterException(__FILE__, __LINE__); +} + +ObjectPrx +Ice::ObjectAdapterI::objectToProxy(const ObjectPtr& object) +{ + string identity = objectToIdentity(object); + + if (identity.empty()) + { + throw WrongObjectAdapterException(__FILE__, __LINE__); + } + + return identityToProxy(identity); +} + +ObjectPrx +Ice::ObjectAdapterI::identityToProxy(const string& identity) +{ + JTCSyncT<JTCMutex> sync(*this); + + if (_collectorFactories.empty()) + { + throw ObjectAdapterDeactivatedException(__FILE__, __LINE__); + } + + vector<EndpointPtr> endpoints; + transform(_collectorFactories.begin(), _collectorFactories.end(), back_inserter(endpoints), + constMemFun(&CollectorFactory::endpoint)); + + ReferencePtr reference = new Reference(_instance, identity, endpoints, endpoints); + return _instance->proxyFactory()->referenceToProxy(reference); +} + +string +Ice::ObjectAdapterI::proxyToIdentity(const ObjectPrx& proxy) +{ + return proxy->__reference()->identity; +} + +Ice::ObjectAdapterI::ObjectAdapterI(const InstancePtr& instance, const string& name, const string& endpts) : + _instance(instance), + _name(name) +{ + string s(endpts); + transform(s.begin(), s.end(), s.begin(), tolower); + + string::size_type beg = 0; + string::size_type end; + + while (true) + { + end = s.find(':', beg); + if (end == string::npos) + { + end = s.length(); + } + + if (end == beg) + { + throw EndpointParseException(__FILE__, __LINE__); + } + + string es = s.substr(beg, end - beg); + + // Don't store the endpoint in the adapter. The Collector + // might change it, for example, to fill in the real port + // number if a zero port number is given. + EndpointPtr endp = Endpoint::endpointFromString(es); + try + { + // Set the "no delete" flag to true, meaning that this + // object will not be deleted, even if the reference count + // drops to zero. This is needed because if the + // constructor of the CollectorFactory throws an + // exception, the only CollectorFactoryPtr reference for + // this object will be the one that is temporarily + // constructed for passing the "this" parameter below. And + // then this temporary reference is destroyed, this object + // would be deleted if we don't set the "no delete" flag. + __setNoDelete(true); + _collectorFactories.push_back(new CollectorFactory(instance, this, endp)); + __setNoDelete(false); + } + catch(...) + { + __setNoDelete(false); + throw; + } + + if (end == s.length()) + { + break; + } + + beg = end + 1; + } + + if (!_collectorFactories.size()) + { + throw EndpointParseException(__FILE__, __LINE__); + } +} + +Ice::ObjectAdapterI::~ObjectAdapterI() +{ + if (!_collectorFactories.empty()) + { + deactivate(); + } +} diff --git a/cpp/src/Ice/ObjectAdapterI.h b/cpp/src/Ice/ObjectAdapterI.h new file mode 100644 index 00000000000..78a0e4e253b --- /dev/null +++ b/cpp/src/Ice/ObjectAdapterI.h @@ -0,0 +1,71 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_OBJECT_ADAPTER_I_H +#define ICE_OBJECT_ADAPTER_I_H + +#include <Ice/ObjectAdapter.h> +#include <Ice/InstanceF.h> +#include <Ice/ObjectAdapterFactoryF.h> +#include <Ice/CommunicatorF.h> +#include <Ice/CollectorF.h> +#include <Ice/ProxyF.h> +#include <Ice/ObjectF.h> +#include <Ice/LocalException.h> +#include <Ice/Shared.h> +#include <map> + +namespace Ice +{ + +class ICE_API ObjectAdapterI : public ObjectAdapter, public JTCMutex +{ +public: + + virtual std::string getName(); + virtual CommunicatorPtr getCommunicator(); + + virtual void activate(); + virtual void hold(); + virtual void deactivate(); + + virtual void add(const ObjectPtr&, const std::string&); + virtual void addTemporary(const ObjectPtr&); + virtual void remove(const std::string&); + + virtual void setObjectLocator(const ObjectLocatorPtr&); + virtual ObjectLocatorPtr getObjectLocator(); + + virtual ObjectPtr identityToObject(const std::string&); + virtual std::string objectToIdentity(const ObjectPtr&); + + virtual ObjectPtr proxyToObject(const ObjectPrx&); + virtual ObjectPrx objectToProxy(const ObjectPtr&); + + virtual ObjectPrx identityToProxy(const std::string&); + virtual std::string proxyToIdentity(const ObjectPrx&); + +private: + + ObjectAdapterI(const ::IceInternal::InstancePtr&, const std::string&, + const std::string&); + virtual ~ObjectAdapterI(); + friend ::IceInternal::ObjectAdapterFactory; + + ::IceInternal::InstancePtr _instance; + std::string _name; + std::vector< IceInternal::CollectorFactoryPtr> _collectorFactories; + std::map<std::string, ObjectPtr> _objects; + ::Ice::ObjectLocatorPtr _locator; +}; + +} + +#endif diff --git a/cpp/src/Ice/Outgoing.cpp b/cpp/src/Ice/Outgoing.cpp new file mode 100644 index 00000000000..9181fbb60b9 --- /dev/null +++ b/cpp/src/Ice/Outgoing.cpp @@ -0,0 +1,236 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/Outgoing.h> +#include <Ice/Object.h> +#include <Ice/Emitter.h> +#include <Ice/Reference.h> +#include <Ice/LocalException.h> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +IceInternal::NonRepeatable::NonRepeatable(const NonRepeatable& ex) +{ + _ex = auto_ptr<LocalException>(ex.get()->clone()); +} + +IceInternal::NonRepeatable::NonRepeatable(const ::Ice::LocalException& ex) +{ + _ex = auto_ptr<LocalException>(ex.clone()); +} + +void +IceInternal::NonRepeatable::raise() const +{ + assert(_ex.get()); + _ex.get()->raise(); +} + +const ::Ice::LocalException* +IceInternal::NonRepeatable::get() const +{ + assert(_ex.get()); + return _ex.get(); +} + +IceInternal::Outgoing::Outgoing(const EmitterPtr& emitter, const ReferencePtr& reference) : + _emitter(emitter), + _reference(reference), + _state(StateUnsent), + _is(reference->instance), + _os(reference->instance) +{ + _emitter->prepareRequest(this); + _os.write(_reference->identity); +} + +IceInternal::Outgoing::~Outgoing() +{ +} + +bool +IceInternal::Outgoing::invoke() +{ + switch (_reference->mode) + { + case Reference::ModeTwoway: + { + bool timedOut = false; + + { + JTCSyncT<JTCMonitorT<JTCMutex> > sync(*this); + + _emitter->sendRequest(this, false); + _state = StateInProgress; + + Int timeout = _emitter->timeout(); + while (_state == StateInProgress) + { + try + { + if (timeout >= 0) + { + wait(timeout); + if (_state == StateInProgress) + { + _state = StateLocalException; + _exception = auto_ptr<LocalException>(new TimeoutException(__FILE__, __LINE__)); + timedOut = true; + } + } + else + { + wait(); + } + } + catch(const JTCInterruptedException&) + { + } + } + } + + if (_exception.get()) + { + if (timedOut) + { + // + // Must be called outside the synchronization of this + // object + // + _emitter->exception(*_exception.get()); + } + + // + // A CloseConnectionException indicates graceful + // server shutdown, and is therefore always repeatable + // without violating "at-most-once". That's because by + // sending a close connection message, the server + // guarantees that all outstanding requests can safely + // be repeated. + // + if(dynamic_cast<const CloseConnectionException*>(_exception.get())) + { + _exception->raise(); + } + + // + // Throw the exception wrapped in a NonRepeatable, to + // indicate that the request cannot be resent without + // potentially violating the "at-most-once" principle. + // + throw NonRepeatable(*_exception.get()); + } + + if (_state == StateException) + { + return false; + } + + if (_state == StateLocationForward) + { + ObjectPrx p; + read(&_is, p); + throw LocationForward(p); + } + + assert(_state == StateOK); + break; + } + + case Reference::ModeOneway: + case Reference::ModeDatagram: + { + _emitter->sendRequest(this, true); + break; + } + } + + return true; +} + +void +IceInternal::Outgoing::finished(Stream& is) +{ + JTCSyncT<JTCMonitorT<JTCMutex> > sync(*this); + if (_state == StateInProgress) + { + _is.swap(is); + Byte status; + _is.read(status); + switch (static_cast<DispatchStatus>(status)) + { + case DispatchOK: + { + _state = StateOK; + break; + } + + case DispatchException: + { + _state = StateException; + break; + } + + case DispatchLocationForward: + { + _state = StateLocationForward; + break; + } + + case DispatchObjectNotExist: + { + _state = StateLocalException; + _exception = auto_ptr<LocalException>(new ObjectNotExistException(__FILE__, __LINE__)); + break; + } + + case DispatchOperationNotExist: + { + _state = StateLocalException; + _exception = auto_ptr<LocalException>(new OperationNotExistException(__FILE__, __LINE__)); + break; + } + + default: + { + _state = StateLocalException; + _exception = auto_ptr<LocalException>(new UnknownReplyStatusException(__FILE__, __LINE__)); + break; + } + } + notify(); + } +} + +void +IceInternal::Outgoing::finished(const LocalException& ex) +{ + JTCSyncT<JTCMonitorT<JTCMutex> > sync(*this); + if (_state == StateInProgress) + { + _state = StateLocalException; + _exception = auto_ptr<LocalException>(ex.clone()); + notify(); + } +} + +Stream* +IceInternal::Outgoing::is() +{ + return &_is; +} + +Stream* +IceInternal::Outgoing::os() +{ + return &_os; +} diff --git a/cpp/src/Ice/PicklerI.cpp b/cpp/src/Ice/PicklerI.cpp new file mode 100644 index 00000000000..297dc15d87f --- /dev/null +++ b/cpp/src/Ice/PicklerI.cpp @@ -0,0 +1,86 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/PicklerI.h> +#include <Ice/Stream.h> +#include <Ice/LocalException.h> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +void +Ice::PicklerI::pickle(const ObjectPtr& obj, std::ostream& out) +{ + Stream s(_instance); + s.startWriteEncaps(); + s.write(obj); + s.endWriteEncaps(); + out.write(s.b.begin(), s.b.size()); + if (!out) + { + throw SystemException(__FILE__, __LINE__); + } +} + +ObjectPtr +Ice::PicklerI::unpickle(std::istream& in) +{ + Stream s(_instance); + s.b.resize(6); + in.read(s.b.begin(), 6); + if (in.eof()) + { + throw UnmarshalOutOfBoundsException(__FILE__, __LINE__); + } + if (!in) + { + throw SystemException(__FILE__, __LINE__); + } + + s.i = s.b.begin(); + bool bigendian; + s.read(bigendian); + s.pushBigendian(bigendian); + Byte encVer; + s.read(encVer); + Int sz; + s.read(sz); + s.popBigendian(); + + // Don't use s.b.resize() here, otherwise no size sanity checks + // will be done + s.resize(6 + sz); + in.read(s.b.begin() + 6, sz); + if (in.eof()) + { + throw UnmarshalOutOfBoundsException(__FILE__, __LINE__); + } + if (!in) + { + throw SystemException(__FILE__, __LINE__); + } + + s.i = s.b.begin(); + s.startReadEncaps(); + ObjectPtr obj; + s.read(obj, "::Ice::Object"); + s.endReadEncaps(); + if (!obj) + { + throw NoFactoryException(__FILE__, __LINE__); + } + return obj; +} + +Ice::PicklerI::PicklerI(const InstancePtr& instance) : + _instance(instance) +{ +} diff --git a/cpp/src/Ice/PicklerI.h b/cpp/src/Ice/PicklerI.h new file mode 100644 index 00000000000..0a378dd8474 --- /dev/null +++ b/cpp/src/Ice/PicklerI.h @@ -0,0 +1,39 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_PICKLER_I_H +#define ICE_PICKLER_I_H + +#include <Ice/Pickler.h> +#include <Ice/InstanceF.h> +#include <Ice/Shared.h> + +namespace Ice +{ + +class ICE_API PicklerI : public Pickler +{ +public: + + void pickle(const ObjectPtr&, std::ostream&); + ObjectPtr unpickle(std::istream&); + +private: + + PicklerI(const ::IceInternal::InstancePtr&); + friend ::IceInternal::Instance; + + ::IceInternal::InstancePtr _instance; +}; + +} + +#endif + diff --git a/cpp/src/Ice/PropertiesI.cpp b/cpp/src/Ice/PropertiesI.cpp new file mode 100644 index 00000000000..58d4e2c123c --- /dev/null +++ b/cpp/src/Ice/PropertiesI.cpp @@ -0,0 +1,95 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/PropertiesI.h> +#include <Ice/LocalException.h> +#include <fstream> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +string +Ice::PropertiesI::getProperty(const string& key) +{ + map<string, string>::const_iterator p = _properties.find(key); + if (p != _properties.end()) + return p->second; + else + return string(); +} + +void +Ice::PropertiesI::setProperty(const string& key, const string& value) +{ + _properties[key] = value; +} + +Ice::PropertiesI::PropertiesI() +{ +} + +Ice::PropertiesI::PropertiesI(const string& file) +{ + load(file); +} + +void +Ice::PropertiesI::load(const std::string& file) +{ + ifstream in(file.c_str()); + if (!in) + throw SystemException(__FILE__, __LINE__); + parse(in); +} + +void +Ice::PropertiesI::parse(istream& in) +{ + const string delim = " \t"; + + char line[1024]; + while (in.getline(line, 1024)) + { + string s = line; + + string::size_type idx = s.find('#'); + if (idx != string::npos) + s.erase(idx); + + idx = s.find_last_not_of(delim); + if (idx != string::npos && idx + 1 < s.length()) + s.erase(idx + 1); + + string::size_type beg = s.find_first_not_of(delim); + if (beg == string::npos) + continue; + + string::size_type end = s.find_first_of(delim + "=", beg); + if (end == string::npos) + continue; + + string key = s.substr(beg, end - beg); + + end = s.find('=', end); + if (end == string::npos) + continue; + + beg = s.find_first_not_of(delim + "=", end); + if (beg == string::npos) + continue; + + end = s.length(); + + string value = s.substr(beg, end - beg); + + setProperty(key, value); + } +} diff --git a/cpp/src/Ice/PropertiesI.h b/cpp/src/Ice/PropertiesI.h new file mode 100644 index 00000000000..b1f51163121 --- /dev/null +++ b/cpp/src/Ice/PropertiesI.h @@ -0,0 +1,45 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_PROPERTIES_I_H +#define ICE_PROPERTIES_I_H + +#include <Ice/Properties.h> +#include <Ice/CommunicatorF.h> +#include <map> + +namespace Ice +{ + +class ICE_API PropertiesI : public Properties +{ +public: + + std::string getProperty(const std::string&); + void setProperty(const std::string&, const std::string&); + +private: + + PropertiesI(); + PropertiesI(const std::string&); + + friend ICE_API CommunicatorPtr initialize(int&, char*[], Int); + friend ICE_API PropertiesPtr createProperties(); + friend ICE_API PropertiesPtr loadProperties(const std::string&); + + void load(const std::string&); + void parse(std::istream&); + + std::map<std::string, std::string> _properties; +}; + +} + +#endif diff --git a/cpp/src/Ice/Proxy.cpp b/cpp/src/Ice/Proxy.cpp new file mode 100644 index 00000000000..af0789dfd3b --- /dev/null +++ b/cpp/src/Ice/Proxy.cpp @@ -0,0 +1,503 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/Proxy.h> +#include <Ice/ProxyFactory.h> +#include <Ice/Object.h> +#include <Ice/ObjectAdapterFactory.h> +#include <Ice/Outgoing.h> +#include <Ice/Reference.h> +#include <Ice/Endpoint.h> +#include <Ice/Instance.h> +#include <Ice/Logger.h> +#include <Ice/TraceLevels.h> +#include <Ice/Emitter.h> +#include <Ice/Stream.h> +#include <Ice/LocalException.h> +#include <Ice/Functional.h> +#include <sstream> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +void IceInternal::incRef(::IceProxy::Ice::Object* p) { p->__incRef(); } +void IceInternal::decRef(::IceProxy::Ice::Object* p) { p->__decRef(); } + +void IceInternal::incRef(::IceDelegate::Ice::Object* p) { p->__incRef(); } +void IceInternal::decRef(::IceDelegate::Ice::Object* p) { p->__decRef(); } + +void IceInternal::incRef(::IceDelegateM::Ice::Object* p) { p->__incRef(); } +void IceInternal::decRef(::IceDelegateM::Ice::Object* p) { p->__decRef(); } + +void +IceInternal::checkedCast(::IceProxy::Ice::Object* b, ::IceProxy::Ice::Object*& d) +{ + d = b; +} + +void +IceInternal::uncheckedCast(::IceProxy::Ice::Object* b, ::IceProxy::Ice::Object*& d) +{ + d = b; +} + +void +IceInternal::write(Stream* s, const ObjectPrx& v) +{ + s->instance()->proxyFactory()->proxyToStream(v, s); +} + +void +IceInternal::read(Stream* s, ObjectPrx& v) +{ + v = s->instance()->proxyFactory()->streamToProxy(s); +} + +Ice::ObjectPrxE::ObjectPrxE(const ObjectPrxE& p) : + _prx(p._prx) +{ +} + +Ice::ObjectPrxE::ObjectPrxE(const ObjectPrx& p) : + _prx(p) +{ +} + +Ice::ObjectPrxE::operator ObjectPrx() const +{ + return _prx; +} + +IceProxy::Ice::Object* +Ice::ObjectPrxE::operator->() const +{ + return _prx.get(); +} + +Ice::ObjectPrxE::operator bool() const +{ + return _prx.get() ? true : false; +} + +void +IceProxy::Ice::Object::_throw() +{ + throw ObjectPrxE(this); +} + +bool +IceProxy::Ice::Object::_isA(const string& s) +{ + int __cnt = 0; + while (true) + { + try + { + Handle< ::IceDelegate::Ice::Object> __del = __getDelegate(); + return __del->_isA(s); + } + catch (const LocationForward& __ex) + { + __locationForward(__ex); + } + catch (const NonRepeatable& __ex) + { + __handleException(*__ex.get(), __cnt); + } + catch (const LocalException& __ex) + { + __handleException(__ex, __cnt); + } + } +} + +void +IceProxy::Ice::Object::_ping() +{ + int __cnt = 0; + while (true) + { + try + { + Handle< ::IceDelegate::Ice::Object> __del = __getDelegate(); + __del->_ping(); + return; + } + catch (const LocationForward& __ex) + { + __locationForward(__ex); + } + catch (const NonRepeatable& __ex) + { + __handleException(*__ex.get(), __cnt); + } + catch (const LocalException& __ex) + { + __handleException(__ex, __cnt); + } + } +} + +bool +IceProxy::Ice::Object::operator==(const Object& r) const +{ + return _reference->identity == r._reference->identity; +} + +bool +IceProxy::Ice::Object::operator!=(const Object& r) const +{ + return _reference->identity != r._reference->identity; +} + +ObjectPrx +IceProxy::Ice::Object::_twoway() const +{ + ReferencePtr ref = _reference->changeMode(Reference::ModeTwoway); + if (ref == _reference) + { + return ObjectPrx(const_cast< ::IceProxy::Ice::Object*>(this)); + } + else + { + ObjectPrx proxy(new ::IceProxy::Ice::Object()); + proxy->setup(ref); + return proxy; + } +} + +ObjectPrx +IceProxy::Ice::Object::_oneway() const +{ + ReferencePtr ref = _reference->changeMode(Reference::ModeOneway); + if (ref == _reference) + { + return ObjectPrx(const_cast< ::IceProxy::Ice::Object*>(this)); + } + else + { + ObjectPrx proxy(new ::IceProxy::Ice::Object()); + proxy->setup(ref); + return proxy; + } +} + +ObjectPrx +IceProxy::Ice::Object::_secure() const +{ + ReferencePtr ref = _reference->changeMode(Reference::ModeSecure); + if (ref == _reference) + { + return ObjectPrx(const_cast< ::IceProxy::Ice::Object*>(this)); + } + else + { + ObjectPrx proxy(new ::IceProxy::Ice::Object()); + proxy->setup(ref); + return proxy; + } +} + +ObjectPrx +IceProxy::Ice::Object::_datagram() const +{ + ReferencePtr ref = _reference->changeMode(Reference::ModeDatagram); + if (ref == _reference) + { + return ObjectPrx(const_cast< ::IceProxy::Ice::Object*>(this)); + } + else + { + ObjectPrx proxy(new ::IceProxy::Ice::Object()); + proxy->setup(ref); + return proxy; + } +} + +ObjectPrx +IceProxy::Ice::Object::_timeout(int t) const +{ + ReferencePtr ref = _reference->changeTimeout(t); + if (ref == _reference) + { + return ObjectPrx(const_cast< ::IceProxy::Ice::Object*>(this)); + } + else + { + ObjectPrx proxy(new ::IceProxy::Ice::Object()); + proxy->setup(ref); + return proxy; + } +} + +ReferencePtr +IceProxy::Ice::Object::__reference() const +{ + return _reference; +} + +void +IceProxy::Ice::Object::__copyTo(::IceProxy::Ice::Object* to) const +{ + to->setup(_reference); +} + +void +IceProxy::Ice::Object::__handleException(const LocalException& ex, int& cnt) +{ + JTCSyncT<JTCMutex> sync(*this); + + _delegate = 0; + static const int max = 1; // TODO: Make number of retries configurable + + try + { + ex.raise(); + } + catch (const NoEndpointException&) + { + // + // We always retry on a no endpoint exception, as we might + // have a forwarded reference, but we retry with the original + // reference. + // + } + catch (const CloseConnectionException&) + { + // + // We always retry on a close connection exception, as this + // indicates graceful server shutdown. + // + // TODO: configurable timeout before we try again? + } + catch (const SocketException&) + { + ++cnt; + } + catch (const DNSException&) + { + ++cnt; + } + +#ifndef ICE_NO_TRACE + TraceLevelsPtr traceLevels = _reference->instance->traceLevels(); + LoggerPtr logger = _reference->instance->logger(); +#endif + + if(cnt > max) + { +#ifndef ICE_NO_TRACE + if (traceLevels->retry >= 1) + { + ostringstream s; + s << "cannot retry operation call because retry limit has been exceeded\n" << ex; + logger->trace(traceLevels->retryCat, s.str()); + } +#endif + ex.raise(); + } + +#ifndef ICE_NO_TRACE + if (traceLevels->retry >= 1) + { + ostringstream s; + s << "re-trying operation call because of exception\n" << ex; + logger->trace(traceLevels->retryCat, s.str()); + } +#endif + + // + // Reset the endpoints to the original endpoints upon retry + // + _reference = _reference->changeEndpoints(_reference->origEndpoints); +} + +void +IceProxy::Ice::Object::__locationForward(const LocationForward& ex) +{ + JTCSyncT<JTCMutex> sync(*this); + + if (_reference->identity != ex._prx->_reference->identity) + { + throw ReferenceIdentityException(__FILE__, __LINE__); + } + + _delegate = 0; + _reference = _reference->changeEndpoints(ex._prx->_reference->endpoints); + +/* +#ifndef ICE_NO_TRACE + TraceLevelsPtr traceLevels = _reference->instance->traceLevels(); + LoggerPtr logger = _reference->instance->logger(); + + if (traceLevels->locationForward >= 1) + { + ostringstream s; + s << "location forward for object with identity `" << _reference.identity << "'"; + logger->trace(traceLevels->locationForwardCat, s.str()); + } +#endif +*/ +} + +IceProxy::Ice::Object::Object() +{ +} + +IceProxy::Ice::Object::~Object() +{ +} + +Handle< ::IceDelegate::Ice::Object> +IceProxy::Ice::Object::__getDelegate() +{ + JTCSyncT<JTCMutex> sync(*this); + + if (!_delegate) + { + ObjectPtr obj = _reference->instance->objectAdapterFactory()->proxyToObject(this); + + if (obj) + { + _delegate = obj; + } + else + { + _delegate = __createDelegateM(); + _delegate->setup(_reference); + } + } + + return _delegate; +} + +Handle< ::IceDelegateM::Ice::Object> +IceProxy::Ice::Object::__createDelegateM() +{ + return Handle< ::IceDelegateM::Ice::Object>(new ::IceDelegateM::Ice::Object); +} + +void +IceProxy::Ice::Object::setup(const ReferencePtr& reference) +{ + // + // No need to synchronize, as this operation is only called + // upon initial initialization. + // + _reference = reference; +} + +IceDelegate::Ice::Object::Object() +{ +} + +IceDelegate::Ice::Object::~Object() +{ +} + +void +IceDelegate::Ice::Object::setup(const ::IceInternal::ReferencePtr&) +{ +} + +bool +IceDelegateM::Ice::Object::_isA(const string& s) +{ + Outgoing __out(__emitter(), __reference()); + Stream* __is = __out.is(); + Stream* __os = __out.os(); + __os->write("_isA"); + __os->write(s); + if (!__out.invoke()) + { + throw ::Ice::UnknownUserException(__FILE__, __LINE__); + } + bool __ret; + __is->read(__ret); + return __ret; +} + +void +IceDelegateM::Ice::Object::_ping() +{ + Outgoing __out(__emitter(), __reference()); + Stream* __os = __out.os(); + __os->write("_ping"); + if (!__out.invoke()) + { + throw ::Ice::UnknownUserException(__FILE__, __LINE__); + } +} + +IceDelegateM::Ice::Object::Object() +{ +} + +IceDelegateM::Ice::Object::~Object() +{ +} + +const EmitterPtr& +IceDelegateM::Ice::Object::__emitter() +{ + return _emitter; +} + +const ReferencePtr& +IceDelegateM::Ice::Object::__reference() +{ + return _reference; +} + +void +IceDelegateM::Ice::Object::setup(const ReferencePtr& reference) +{ + // + // No need to synchronize, as this operation is only called + // upon initial initialization. + // + _reference = reference; + vector<EndpointPtr> endpoints; + switch (_reference->mode) + { + case Reference::ModeTwoway: + case Reference::ModeOneway: + { + remove_copy_if(_reference->endpoints.begin(), _reference->endpoints.end(), back_inserter(endpoints), + not1(constMemFun(&Endpoint::regular))); + break; + } + + case Reference::ModeDatagram: + { + remove_copy_if(_reference->endpoints.begin(), _reference->endpoints.end(), back_inserter(endpoints), + not1(constMemFun(&Endpoint::datagram))); + break; + } + + case Reference::ModeSecure: + { + remove_copy_if(_reference->endpoints.begin(), _reference->endpoints.end(), back_inserter(endpoints), + not1(constMemFun(&Endpoint::secure))); + break; + } + } + + if (endpoints.empty()) + { + throw NoEndpointException(__FILE__, __LINE__); + } + + random_shuffle(endpoints.begin(), endpoints.end()); + + EmitterFactoryPtr factory = _reference->instance->emitterFactory(); + _emitter = factory->create(endpoints); +} diff --git a/cpp/src/Ice/ProxyFactory.cpp b/cpp/src/Ice/ProxyFactory.cpp new file mode 100644 index 00000000000..d15f7debb7b --- /dev/null +++ b/cpp/src/Ice/ProxyFactory.cpp @@ -0,0 +1,78 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/ProxyFactory.h> +#include <Ice/Instance.h> +#include <Ice/Proxy.h> +#include <Ice/Reference.h> +#include <Ice/Endpoint.h> +#include <Ice/Stream.h> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +void IceInternal::incRef(ProxyFactory* p) { p->__incRef(); } +void IceInternal::decRef(ProxyFactory* p) { p->__decRef(); } + +ObjectPrx +IceInternal::ProxyFactory::stringToProxy(const string& s) +{ + ReferencePtr reference = new Reference(_instance, s); + return referenceToProxy(reference); +} + +ObjectPrx +IceInternal::ProxyFactory::streamToProxy(Stream* s) +{ + Stream::Container::iterator i = s->i; + string identity; + s->read(identity); + if (identity.length() == 0) + { + return 0; + } + else + { + s->i = i; + ReferencePtr reference = new Reference(s); + return referenceToProxy(reference); + } +} + +ObjectPrx +IceInternal::ProxyFactory::referenceToProxy(const ReferencePtr& reference) +{ + ObjectPrx proxy = new ::IceProxy::Ice::Object; + proxy->setup(reference); + return proxy; +} + +void +IceInternal::ProxyFactory::proxyToStream(const ObjectPrx& proxy, Stream* s) +{ + if (proxy) + { + proxy->__reference()->streamWrite(s); + } + else + { + s->write(""); + } +} + +IceInternal::ProxyFactory::ProxyFactory(const InstancePtr& instance) + : _instance(instance) +{ +} + +IceInternal::ProxyFactory::~ProxyFactory() +{ +} diff --git a/cpp/src/Ice/ProxyFactory.h b/cpp/src/Ice/ProxyFactory.h new file mode 100644 index 00000000000..fb0cc851685 --- /dev/null +++ b/cpp/src/Ice/ProxyFactory.h @@ -0,0 +1,45 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_PROXY_FACTORY_H +#define ICE_PROXY_FACTORY_H + +#include <Ice/ProxyFactoryF.h> +#include <Ice/InstanceF.h> +#include <Ice/ReferenceF.h> +#include <Ice/ProxyF.h> +#include <Ice/Shared.h> + +namespace IceInternal +{ + +class Stream; + +class ProxyFactory : public Shared +{ +public: + + ::Ice::ObjectPrx stringToProxy(const std::string&); + ::Ice::ObjectPrx streamToProxy(Stream*); + ::Ice::ObjectPrx referenceToProxy(const ReferencePtr&); + void proxyToStream(const ::Ice::ObjectPrx&, Stream*); + +private: + + ProxyFactory(const InstancePtr&); + virtual ~ProxyFactory(); + friend class Instance; + + InstancePtr _instance; +}; + +} + +#endif diff --git a/cpp/src/Ice/Reference.cpp b/cpp/src/Ice/Reference.cpp new file mode 100644 index 00000000000..832a5eecc55 --- /dev/null +++ b/cpp/src/Ice/Reference.cpp @@ -0,0 +1,343 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/Reference.h> +#include <Ice/Endpoint.h> +#include <Ice/Stream.h> +#include <Ice/LocalException.h> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +void IceInternal::incRef(Reference* p) { p->__incRef(); } +void IceInternal::decRef(Reference* p) { p->__decRef(); } + +IceInternal::Reference::Reference(const InstancePtr& inst, const string& ident, + const vector<EndpointPtr>& origEndpts, const vector<EndpointPtr>& endpts) : + instance(inst), + identity(ident), + mode(ModeTwoway), + origEndpoints(origEndpts), + endpoints(endpts) +{ +} + +IceInternal::Reference::Reference(const InstancePtr& inst, const string& str) : + instance(inst), + mode(ModeTwoway) +{ + const string delim = " \t\n\r"; + + string s(str); + transform(s.begin(), s.end(), s.begin(), tolower); + + string::size_type beg; + string::size_type end = 0; + + beg = s.find_first_not_of(delim, end); + if (beg == string::npos) + { + throw ReferenceParseException(__FILE__, __LINE__); + } + + end = s.find_first_of(delim + ":", beg); + if (end == string::npos) + { + end = s.length(); + } + + if (beg == end) + { + throw ReferenceParseException(__FILE__, __LINE__); + } + + const_cast<string&>(identity) = s.substr(beg, end - beg); + + while (true) + { + beg = s.find_first_not_of(delim, end); + if (beg == string::npos) + { + break; + } + + end = s.find_first_of(delim + ":", beg); + if (end == string::npos) + { + end = s.length(); + } + + if (beg == end) + { + break; + } + + string option = s.substr(beg, end - beg); + if (option.length() != 2 || option[0] != '-') + { + throw ReferenceParseException(__FILE__, __LINE__); + } + + switch (option[1]) + { + case 't': + { + const_cast<Mode&>(mode) = ModeTwoway; + break; + } + + case 'o': + { + const_cast<Mode&>(mode) = ModeOneway; + break; + } + + case 's': + { + const_cast<Mode&>(mode) = ModeSecure; + break; + } + + case 'd': + { + const_cast<Mode&>(mode) = ModeDatagram; + break; + } + + default: + { + throw ReferenceParseException(__FILE__, __LINE__); + } + } + } + + while (end < s.length() && s[end] == ':') + { + beg = end + 1; + + end = s.find(':', beg); + if (end == string::npos) + { + end = s.length(); + } + + string es = s.substr(beg, end - beg); + EndpointPtr endp = Endpoint::endpointFromString(es); + const_cast<vector<EndpointPtr>&>(origEndpoints).push_back(endp); + } + + if (!origEndpoints.size()) + { + throw ReferenceParseException(__FILE__, __LINE__); + } + + const_cast<vector<EndpointPtr>&>(endpoints) = origEndpoints; +} + +IceInternal::Reference::Reference(Stream* s) : + instance(s->instance()), + mode(ModeTwoway) +{ + s->read(const_cast<string&>(identity)); + + vector<EndpointPtr>::const_iterator p; + Ice::Int sz; + + s->read(sz); + const_cast<vector<EndpointPtr>&>(origEndpoints).resize(sz); + for (p = origEndpoints.begin(); p != origEndpoints.end(); ++p) + { + Endpoint::streamRead(s, const_cast<EndpointPtr&>(*p)); + } + + bool same; + s->read(same); + if (same) // origEndpoints == endpoints + { + const_cast<vector<EndpointPtr>&>(endpoints) = origEndpoints; + } + else + { + s->read(sz); + const_cast<vector<EndpointPtr>&>(endpoints).resize(sz); + for (p = endpoints.begin(); p != endpoints.end(); ++p) + { + Endpoint::streamRead(s, const_cast<EndpointPtr&>(*p)); + } + } +} + +void +IceInternal::Reference::streamWrite(Stream* s) const +{ + s->write(identity); + + s->write(Ice::Int(origEndpoints.size())); + vector<EndpointPtr>::const_iterator p; + for (p = origEndpoints.begin(); p != origEndpoints.end(); ++p) + { + (*p)->streamWrite(s); + } + + if(endpoints == origEndpoints) + { + s->write(true); + } + else + { + s->write(Ice::Int(endpoints.size())); + vector<EndpointPtr>::const_iterator p; + for (p = endpoints.begin(); p != endpoints.end(); ++p) + { + (*p)->streamWrite(s); + } + } +} + +ReferencePtr +IceInternal::Reference::changeTimeout(int timeout) const +{ + vector<EndpointPtr>::const_iterator p; + + vector<EndpointPtr> newOrigEndpoints; + for (p = origEndpoints.begin(); p != origEndpoints.end(); ++p) + { + newOrigEndpoints.push_back((*p)->timeout(timeout)); + } + + vector<EndpointPtr> newEndpoints; + for (p = endpoints.begin(); p != endpoints.end(); ++p) + { + newEndpoints.push_back((*p)->timeout(timeout)); + } + + ReferencePtr ref(new Reference(instance, identity, newOrigEndpoints, newEndpoints)); + + if (*ref.get() == *this) + { + return ReferencePtr(const_cast<Reference*>(this)); + } + + return ref; +} + +ReferencePtr +IceInternal::Reference::changeMode(Mode m) const +{ + if (m == mode) + { + return ReferencePtr(const_cast<Reference*>(this)); + } + else + { + ReferencePtr ref(new Reference(instance, identity, origEndpoints, endpoints)); + const_cast<Mode&>(ref->mode) = m; + return ref; + } +} + +ReferencePtr +IceInternal::Reference::changeEndpoints(const std::vector<EndpointPtr>& endpts) const +{ + if (endpts == endpoints) + { + return ReferencePtr(const_cast<Reference*>(this)); + } + else + { + ReferencePtr ref(new Reference(instance, identity, origEndpoints, endpts)); + return ref; + } +} + +bool +IceInternal::Reference::operator==(const Reference& r) const +{ + return !operator!=(r); +} + +bool +IceInternal::Reference::operator!=(const Reference& r) const +{ + if (this == &r) + { + return false; + } + + if (identity != r.identity) + { + return true; + } + + if (mode != r.mode) + { + return true; + } + + if (origEndpoints != r.origEndpoints) + { + return true; + } + + if (endpoints != r.endpoints) + { + return true; + } + + return false; +} + +bool +IceInternal::Reference::operator<(const Reference& r) const +{ + if (this == &r) + { + return false; + } + + if (identity < r.identity) + { + return true; + } + else if (identity != r.identity) + { + return false; + } + + if (mode < r.mode) + { + return true; + } + else if (mode != r.mode) + { + return false; + } + + if (origEndpoints < r.origEndpoints) + { + return true; + } + else if (origEndpoints != r.origEndpoints) + { + return false; + } + + if (endpoints < r.endpoints) + { + return true; + } + else if (endpoints != r.endpoints) + { + return false; + } + + return false; +} diff --git a/cpp/src/Ice/Reference.h b/cpp/src/Ice/Reference.h new file mode 100644 index 00000000000..0453b71e07d --- /dev/null +++ b/cpp/src/Ice/Reference.h @@ -0,0 +1,68 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_REFERENCE_H +#define ICE_REFERENCE_H + +#include <Ice/ReferenceF.h> +#include <Ice/EndpointF.h> +#include <Ice/InstanceF.h> +#include <Ice/Shared.h> + +namespace IceInternal +{ + +class Stream; + +class Reference : public Shared +{ +public: + + Reference(const InstancePtr&, const std::string&, + const std::vector<EndpointPtr>&, const std::vector<EndpointPtr>&); + Reference(const InstancePtr&, const std::string&); + Reference(Stream*); + + void streamWrite(Stream*) const; + + // + // All members are const, because References are immutable. + // + const InstancePtr instance; + const std::string identity; + + enum Mode + { + ModeTwoway, + ModeOneway, + ModeSecure, + ModeDatagram + }; + const Mode mode; + + const std::vector<EndpointPtr> origEndpoints; // Original endpoints + const std::vector<EndpointPtr> endpoints; // Actual endpoints (set by a location forward) + + // + // Get a new reference, based on the existing one, overwriting + // certain values. + // + ReferencePtr changeTimeout(int) const; + ReferencePtr changeMode(Mode) const; + ReferencePtr changeEndpoints(const std::vector<EndpointPtr>&) const; + + bool operator==(const Reference&) const; + bool operator!=(const Reference&) const; + bool operator<(const Reference&) const; +}; + +} + +#endif diff --git a/cpp/src/Ice/Shared.cpp b/cpp/src/Ice/Shared.cpp new file mode 100644 index 00000000000..84ed34d0aa2 --- /dev/null +++ b/cpp/src/Ice/Shared.cpp @@ -0,0 +1,43 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/Shared.h> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +//static int simpleDebugCounter = 0; +//static int debugCounter = 0; +//static JTCMutex debugCounterMutex; + +IceInternal::SimpleShared::SimpleShared() : + _ref(0) +{ +// cout << "new SimpleShared: " << ++simpleDebugCounter << endl; +} + +IceInternal::SimpleShared::~SimpleShared() +{ +// cout << "delete SimpleShared: " << --simpleDebugCounter << endl; +} + +IceInternal::Shared::Shared() : + _ref(0) +{ +// JTCSyncT<JTCMutex> sync(debugCounterMutex); +// cout << "new Shared: " << ++debugCounter << endl; +} + +IceInternal::Shared::~Shared() +{ +// JTCSyncT<JTCMutex> sync(debugCounterMutex); +// cout << "delete Shared: " << --debugCounter << endl; +} diff --git a/cpp/src/Ice/SslAcceptor.cpp b/cpp/src/Ice/SslAcceptor.cpp new file mode 100644 index 00000000000..56717319e9d --- /dev/null +++ b/cpp/src/Ice/SslAcceptor.cpp @@ -0,0 +1,151 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/SslAcceptor.h> +#include <Ice/SslTransceiver.h> +#include <Ice/Instance.h> +#include <Ice/TraceLevels.h> +#include <Ice/Logger.h> +#include <Ice/Network.h> +#include <Ice/LocalException.h> +#include <sstream> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +int +IceInternal::SslAcceptor::fd() +{ + return _fd; +} + +void +IceInternal::SslAcceptor::close() +{ +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 1) + { + ostringstream s; + s << "stopping to accept connections at " << toString(); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + + int fd = _fd; + _fd = INVALID_SOCKET; + closeSocket(fd); +} + +void +IceInternal::SslAcceptor::shutdown() +{ +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 2) + { + ostringstream s; + s << "shutting down accepting connections at " << toString(); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + + ::shutdown(_fd, SHUT_RD); // Shutdown socket for reading +} + +void +IceInternal::SslAcceptor::listen() +{ + try + { + doListen(_fd, _backlog); + } + catch(...) + { + _fd = INVALID_SOCKET; + throw; + } + +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 1) + { + ostringstream s; + s << "accepting connections at " << toString(); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif +} + +TransceiverPtr +IceInternal::SslAcceptor::accept(int timeout) +{ + int fd = doAccept(_fd, timeout); +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 1) + { + ostringstream s; + s << "accepted connection\n" << fdToString(fd); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + return new SslTransceiver(_instance, fd); +} + +string +IceInternal::SslAcceptor::toString() const +{ + return addrToString(_addr); +} + +bool +IceInternal::SslAcceptor::equivalent(const string& host, int port) const +{ + struct sockaddr_in addr; + getAddress(host.c_str(), port, addr); + if (addr.sin_addr.s_addr == htonl(INADDR_LOOPBACK)) + return port == ntohs(_addr.sin_port); + + struct sockaddr_in localAddr; + getLocalAddress(ntohs(_addr.sin_port), localAddr); + return memcmp(&addr, &localAddr, sizeof(struct sockaddr_in)) == 0; +} + +IceInternal::SslAcceptor::SslAcceptor(const InstancePtr& instance, int port) : + _instance(instance), + _backlog(0) +{ +#ifndef ICE_NO_TRACE + _traceLevels = _instance->traceLevels(); + _logger = _instance->logger(); +#endif + + if (_backlog <= 0) + _backlog = 5; + + try + { + memset(&_addr, 0, sizeof(_addr)); + _addr.sin_family = AF_INET; + _addr.sin_port = htons(port); + _addr.sin_addr.s_addr = htonl(INADDR_ANY); + + _fd = createSocket(false); + doBind(_fd, _addr); + } + catch(...) + { + _fd = INVALID_SOCKET; + throw; + } +} + +IceInternal::SslAcceptor::~SslAcceptor() +{ + assert(_fd == INVALID_SOCKET); +} diff --git a/cpp/src/Ice/SslAcceptor.h b/cpp/src/Ice/SslAcceptor.h new file mode 100644 index 00000000000..b1b98faeab8 --- /dev/null +++ b/cpp/src/Ice/SslAcceptor.h @@ -0,0 +1,60 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_SSL_ACCEPTOR_H +#define ICE_SSL_ACCEPTOR_H + +#include <Ice/TransceiverF.h> +#include <Ice/InstanceF.h> +#include <Ice/TraceLevelsF.h> +#include <Ice/LoggerF.h> +#include <Ice/Acceptor.h> + +#ifndef WIN32 +# include <netinet/in.h> // For struct sockaddr_in +#endif + +namespace IceInternal +{ + +class SslEndpoint; + +class SslAcceptor : public Acceptor +{ +public: + + virtual int fd(); + virtual void close(); + virtual void shutdown(); + virtual void listen(); + virtual TransceiverPtr accept(int); + virtual std::string toString() const; + + virtual bool equivalent(const std::string&, int) const; + +private: + + SslAcceptor(const InstancePtr&, int); + virtual ~SslAcceptor(); + friend class SslEndpoint; + + InstancePtr _instance; + int _fd; + int _backlog; + struct sockaddr_in _addr; +#ifndef ICE_NO_TRACE + TraceLevelsPtr _traceLevels; + ::Ice::LoggerPtr _logger; +#endif +}; + +} + +#endif diff --git a/cpp/src/Ice/SslConnector.cpp b/cpp/src/Ice/SslConnector.cpp new file mode 100644 index 00000000000..630dc1af8cd --- /dev/null +++ b/cpp/src/Ice/SslConnector.cpp @@ -0,0 +1,70 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/SslConnector.h> +#include <Ice/SslTransceiver.h> +#include <Ice/Instance.h> +#include <Ice/TraceLevels.h> +#include <Ice/Logger.h> +#include <Ice/Network.h> +#include <Ice/LocalException.h> +#include <sstream> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +TransceiverPtr +IceInternal::SslConnector::connect(int timeout) +{ +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 2) + { + ostringstream s; + s << "trying to connect to " << toString(); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + + int fd = createSocket(false); + doConnect(fd, _addr, timeout); + +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 1) + { + ostringstream s; + s << "connection established\n" << fdToString(fd); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + + return new SslTransceiver(_instance, fd); +} + +string +IceInternal::SslConnector::toString() const +{ + return addrToString(_addr); +} + +IceInternal::SslConnector::SslConnector(const InstancePtr& instance, const string& host, int port) : + _instance(instance) +{ +#ifndef ICE_NO_TRACE + _traceLevels = _instance->traceLevels(); + _logger = _instance->logger(); +#endif + + getAddress(host.c_str(), port, _addr); +} + +IceInternal::SslConnector::~SslConnector() +{ +} diff --git a/cpp/src/Ice/SslConnector.h b/cpp/src/Ice/SslConnector.h new file mode 100644 index 00000000000..12a3921a017 --- /dev/null +++ b/cpp/src/Ice/SslConnector.h @@ -0,0 +1,52 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_SSL_CONNECTOR_H +#define ICE_SSL_CONNECTOR_H + +#include <Ice/TransceiverF.h> +#include <Ice/InstanceF.h> +#include <Ice/TraceLevelsF.h> +#include <Ice/LoggerF.h> +#include <Ice/Connector.h> + +#ifndef WIN32 +# include <netinet/in.h> // For struct sockaddr_in +#endif + +namespace IceInternal +{ + +class SslEndpoint; + +class SslConnector : public Connector +{ +public: + + virtual TransceiverPtr connect(int); + virtual std::string toString() const; + +private: + + SslConnector(const InstancePtr&, const std::string&, int); + virtual ~SslConnector(); + friend class SslEndpoint; + + InstancePtr _instance; + struct sockaddr_in _addr; +#ifndef ICE_NO_TRACE + TraceLevelsPtr _traceLevels; + ::Ice::LoggerPtr _logger; +#endif +}; + +} + +#endif diff --git a/cpp/src/Ice/SslTransceiver.cpp b/cpp/src/Ice/SslTransceiver.cpp new file mode 100644 index 00000000000..eeb334ae0c5 --- /dev/null +++ b/cpp/src/Ice/SslTransceiver.cpp @@ -0,0 +1,263 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/SslTransceiver.h> +#include <Ice/Instance.h> +#include <Ice/TraceLevels.h> +#include <Ice/Logger.h> +#include <Ice/Buffer.h> +#include <Ice/Network.h> +#include <Ice/LocalException.h> +#include <sstream> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +int +IceInternal::SslTransceiver::fd() +{ + return _fd; +} + +void +IceInternal::SslTransceiver::close() +{ +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 1) + { + ostringstream s; + s << "closing connection\n" << toString(); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + + int fd = _fd; + _fd = INVALID_SOCKET; + ::shutdown(fd, SHUT_RDWR); // helps to unblock threads in recv() + closeSocket(fd); +} + +void +IceInternal::SslTransceiver::shutdown() +{ +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 2) + { + ostringstream s; + s << "shutting down connection\n" << toString(); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + + ::shutdown(_fd, SHUT_WR); // Shutdown socket for writing +} + +void +IceInternal::SslTransceiver::write(Buffer& buf, int timeout) +{ + int packetSize = buf.b.end() - buf.i; + +#ifdef WIN32 + // + // Limit packet size to avoid performance problems on WIN32 + // + if (packetSize > 64 * 1024) + packetSize = 64 * 1024; +#endif + + while (buf.i != buf.b.end()) + { + int ret = ::send(_fd, buf.i, packetSize, 0); + + if (ret == 0) + { +#ifdef WIN32 + WSASetLastError(0); +#else + errno = 0; +#endif + throw ConnectionLostException(__FILE__, __LINE__); + } + + if (ret == SOCKET_ERROR) + { + if (interrupted()) + continue; + + if (noBuffers() && packetSize > 1024) + { + packetSize /= 2; + continue; + } + + if (wouldBlock()) + { + int fd = _fd; // Copy fd, in case another thread calls close() + if (fd != -1) + { + repeatSelect: + int ret; + FD_SET(fd, &wFdSet); + if (timeout >= 0) + { + struct timeval tv; + tv.tv_sec = timeout / 1000; + tv.tv_usec = (timeout - tv.tv_sec * 1000) * 1000; + ret = ::select(fd + 1, 0, &wFdSet, 0, &tv); + } + else + ret = ::select(fd + 1, 0, &wFdSet, 0, 0); + + if (ret == SOCKET_ERROR) + { + if (interrupted()) + goto repeatSelect; + + throw SocketException(__FILE__, __LINE__); + } + + if (ret == 0) + throw TimeoutException(__FILE__, __LINE__); + } + + continue; + } + + if (connectionLost()) + throw ConnectionLostException(__FILE__, __LINE__); + else + throw SocketException(__FILE__, __LINE__); + } + +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 3) + { + ostringstream s; + s << "sent " << ret << " of " << packetSize << " bytes via SSL\n" << toString(); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + + buf.i += ret; + + if (packetSize > buf.b.end() - buf.i) + packetSize = buf.b.end() - buf.i; + } +} + +void +IceInternal::SslTransceiver::read(Buffer& buf, int timeout) +{ + int packetSize = buf.b.end() - buf.i; + + while (buf.i != buf.b.end()) + { + int ret = ::recv(_fd, buf.i, packetSize, 0); + + if (ret == 0) + { +#ifdef WIN32 + WSASetLastError(0); +#else + errno = 0; +#endif + throw ConnectionLostException(__FILE__, __LINE__); + } + + if (ret == SOCKET_ERROR) + { + if (interrupted()) + continue; + + if (noBuffers() && packetSize > 1024) + { + packetSize /= 2; + continue; + } + + if (wouldBlock()) + { + int fd = _fd; // Copy fd, in case another thread calls close() + if (fd != -1) + { + repeatSelect: + int ret; + FD_SET(fd, &rFdSet); + if (timeout >= 0) + { + struct timeval tv; + tv.tv_sec = timeout / 1000; + tv.tv_usec = (timeout - tv.tv_sec * 1000) * 1000; + ret = ::select(fd + 1, &rFdSet, 0, 0, &tv); + } + else + ret = ::select(fd + 1, &rFdSet, 0, 0, 0); + + if (ret == SOCKET_ERROR) + { + if (interrupted()) + goto repeatSelect; + + throw SocketException(__FILE__, __LINE__); + } + + if (ret == 0) + throw TimeoutException(__FILE__, __LINE__); + } + + continue; + } + + if (connectionLost()) + throw ConnectionLostException(__FILE__, __LINE__); + else + throw SocketException(__FILE__, __LINE__); + } + +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 3) + { + ostringstream s; + s << "received " << ret << " of " << packetSize << " bytes via SSL\n" << toString(); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + + buf.i += ret; + + if (packetSize > buf.b.end() - buf.i) + packetSize = buf.b.end() - buf.i; + } +} + +string +IceInternal::SslTransceiver::toString() const +{ + return fdToString(_fd); +} + +IceInternal::SslTransceiver::SslTransceiver(const InstancePtr& instance, int fd) : + _instance(instance), + _fd(fd) +{ + FD_ZERO(&rFdSet); + FD_ZERO(&wFdSet); + +#ifndef ICE_NO_TRACE + _traceLevels = _instance->traceLevels(); + _logger = _instance->logger(); +#endif +} + +IceInternal::SslTransceiver::~SslTransceiver() +{ + assert(_fd == INVALID_SOCKET); +} diff --git a/cpp/src/Ice/SslTransceiver.h b/cpp/src/Ice/SslTransceiver.h new file mode 100644 index 00000000000..680f39358fa --- /dev/null +++ b/cpp/src/Ice/SslTransceiver.h @@ -0,0 +1,55 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_SSL_TRANSCEIVER_H +#define ICE_SSL_TRANSCEIVER_H + +#include <Ice/InstanceF.h> +#include <Ice/TraceLevelsF.h> +#include <Ice/LoggerF.h> +#include <Ice/Transceiver.h> + +namespace IceInternal +{ + +class SslConnector; +class SslAcceptor; + +class SslTransceiver : public Transceiver +{ +public: + + virtual int fd(); + virtual void close(); + virtual void shutdown(); + virtual void write(Buffer&, int); + virtual void read(Buffer&, int); + virtual std::string toString() const; + +private: + + SslTransceiver(const InstancePtr&, int); + virtual ~SslTransceiver(); + friend class SslConnector; + friend class SslAcceptor; + + InstancePtr _instance; + int _fd; + fd_set rFdSet; + fd_set wFdSet; +#ifndef ICE_NO_TRACE + TraceLevelsPtr _traceLevels; + ::Ice::LoggerPtr _logger; +#endif +}; + +} + +#endif diff --git a/cpp/src/Ice/Stream.cpp b/cpp/src/Ice/Stream.cpp new file mode 100644 index 00000000000..adc744616fa --- /dev/null +++ b/cpp/src/Ice/Stream.cpp @@ -0,0 +1,857 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/Stream.h> +#include <Ice/Instance.h> +#include <Ice/Object.h> +#include <Ice/ValueFactory.h> +#include <Ice/ValueFactoryManager.h> +#include <Ice/LocalException.h> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +static const Byte stringEncodingNormal = 0; +static const Byte stringEncodingRedirect = 1; + +IceInternal::Stream::Stream(const InstancePtr& instance) : + _instance(instance), + _bigendian(false), + _stringSet(CmpPosPos(b)) +{ +} + +InstancePtr +IceInternal::Stream::instance() const +{ + return _instance; +} + +void +IceInternal::Stream::swap(Stream& other) +{ + b.swap(other.b); + std::swap(i, other.i); + std::swap(_bigendian, other._bigendian); +} + +void +IceInternal::Stream::resize(int total) +{ + if (total > 1024 * 1024) // TODO: configurable + { + throw ::Ice::MemoryLimitException(__FILE__, __LINE__); + } + + b.resize(total); +} + +void +IceInternal::Stream::reserve(int total) +{ + if (total > 1024 * 1024) // TODO: configurable + { + throw ::Ice::MemoryLimitException(__FILE__, __LINE__); + } + + b.reserve(total); +} + +void +IceInternal::Stream::pushBigendian(bool bigendian) +{ + _bigendianStack.push(bigendian); + _bigendian = _bigendianStack.top(); +} + +void +IceInternal::Stream::popBigendian() +{ + _bigendianStack.pop(); + if (!_bigendianStack.empty()) + { + _bigendian = _bigendianStack.top(); + } + else + { + _bigendian = false; + } +} + +bool +IceInternal::Stream::bigendian() const +{ + return _bigendian; +} + +void +IceInternal::Stream::startWriteEncaps() +{ + write(_bigendian); + write(Byte(0)); // Encoding version + write(Int(0)); // Placeholder for the encapsulation length + _encapsStartStack.push(b.size()); +} + +void +IceInternal::Stream::endWriteEncaps() +{ + int start = _encapsStartStack.top(); + _encapsStartStack.pop(); + Int sz = b.size() - start; + const Byte* p = reinterpret_cast<const Byte*>(&sz); + copy(p, p + sizeof(Int), b.begin() + start - sizeof(Int)); +} + +void +IceInternal::Stream::startReadEncaps() +{ + bool bigendian; + read(bigendian); + pushBigendian(bigendian); + + // + // If in the future several encoding versions are supported, we + // need a pushEncoding() and popEncoding() operation, just like + // pushBigendian() and popBigendian(). + // + Byte encVer; + read(encVer); + if (encVer != 0) + { + throw UnsupportedEncodingException(__FILE__, __LINE__); + } + + Int sz; + read(sz); + _encapsStartStack.push(i - b.begin()); +} + +void +IceInternal::Stream::endReadEncaps() +{ + int start = _encapsStartStack.top(); + _encapsStartStack.pop(); + Container::iterator save = i; + i = b.begin() + start - sizeof(Int); + Int sz; + read(sz); + i = save; + if (sz != i - (b.begin() + start)) + { + throw EncapsulationException(__FILE__, __LINE__); + } + popBigendian(); +} + +void +IceInternal::Stream::skipEncaps() +{ + bool bigendian; + read(bigendian); + pushBigendian(bigendian); + Byte encVer; + read(encVer); + + Int sz; + read(sz); + i += sz; + if (i >= b.end()) + { + throw UnmarshalOutOfBoundsException(__FILE__, __LINE__); + } + + popBigendian(); +} + +void +IceInternal::Stream::write(const vector<Byte>& v) +{ + int pos = b.size(); + Int sz = v.size(); + resize(pos + sizeof(Int) + sz); + const Byte* p = reinterpret_cast<const Byte*>(&sz); + copy(p, p + sizeof(Int), b.begin() + pos); + copy(v.begin(), v.end(), b.begin() + pos + sizeof(Int)); +} + +void +IceInternal::Stream::read(Byte& v) +{ + if (i >= b.end()) + { + throw UnmarshalOutOfBoundsException(__FILE__, __LINE__); + } + + v = *i++; +} + +void +IceInternal::Stream::read(vector<Byte>& v) +{ + Int sz; + read(sz); + + Container::iterator begin = i; + i += sz; + if (i > b.end()) + { + throw UnmarshalOutOfBoundsException(__FILE__, __LINE__); + } + + v.resize(sz); + copy(begin, i, v.begin()); +} + +void +IceInternal::Stream::write(const vector<bool>& v) +{ + int pos = b.size(); + Int sz = v.size(); + resize(pos + sizeof(Int) + sz); + const Byte* p = reinterpret_cast<const Byte*>(&sz); + copy(p, p + sizeof(Int), b.begin() + pos); + copy(v.begin(), v.end(), b.begin() + pos + sizeof(Int)); +} + +void +IceInternal::Stream::read(bool& v) +{ + if (i >= b.end()) + { + throw UnmarshalOutOfBoundsException(__FILE__, __LINE__); + } + + v = *i++; +} + +void +IceInternal::Stream::read(vector<bool>& v) +{ + Int sz; + read(sz); + + Container::iterator begin = i; + i += sz; + if (i > b.end()) + { + throw UnmarshalOutOfBoundsException(__FILE__, __LINE__); + } + + v.resize(sz); + copy(begin, i, v.begin()); +} + +void +IceInternal::Stream::write(Short v) +{ + int pos = b.size(); + resize(pos + sizeof(Short)); + const Byte* p = reinterpret_cast<const Byte*>(&v); + copy(p, p + sizeof(Short), b.begin() + pos); +} + +void +IceInternal::Stream::write(const vector<Short>& v) +{ + int pos = b.size(); + Int sz = v.size(); + resize(pos + sizeof(Int) + sz * sizeof(Short)); + const Byte* p = reinterpret_cast<const Byte*>(&sz); + copy(p, p + sizeof(Int), b.begin() + pos); + p = reinterpret_cast<const Byte*>(v.begin()); + copy(p, p + sz * sizeof(Short), b.begin() + pos + sizeof(Int)); +} + +void +IceInternal::Stream::read(Short& v) +{ + Container::iterator begin = i; + i += sizeof(Short); + if (i > b.end()) + { + throw UnmarshalOutOfBoundsException(__FILE__, __LINE__); + } + + if (_bigendian != ::IceInternal::bigendian) + { + reverse_copy(begin, i, reinterpret_cast<Byte*>(&v)); + } + else + { + copy(begin, i, reinterpret_cast<Byte*>(&v)); + } +} + +void +IceInternal::Stream::read(vector<Short>& v) +{ + Int sz; + read(sz); + + Container::iterator begin = i; + i += sz * sizeof(Short); + if (i > b.end()) + { + throw UnmarshalOutOfBoundsException(__FILE__, __LINE__); + } + + v.resize(sz); + if (_bigendian != ::IceInternal::bigendian) + { + for (int j = 0 ; j < sz ; ++j) + { + reverse_copy(begin, begin + sizeof(Short), reinterpret_cast<Byte*>(&v[j])); + begin += sizeof(Short); + } + } + else + { + copy(begin, i, reinterpret_cast<Byte*>(v.begin())); + } +} + +void +IceInternal::Stream::write(Int v) +{ + int pos = b.size(); + resize(pos + sizeof(Int)); + const Byte* p = reinterpret_cast<const Byte*>(&v); + copy(p, p + sizeof(Int), b.begin() + pos); +} + +void +IceInternal::Stream::write(const vector<Int>& v) +{ + int pos = b.size(); + Int sz = v.size(); + resize(pos + sizeof(Int) + sz * sizeof(Int)); + const Byte* p = reinterpret_cast<const Byte*>(&sz); + copy(p, p + sizeof(Int), b.begin() + pos); + p = reinterpret_cast<const Byte*>(v.begin()); + copy(p, p + sz * sizeof(Int), b.begin() + pos + sizeof(Int)); +} + +void +IceInternal::Stream::read(Int& v) +{ + Container::iterator begin = i; + i += sizeof(Int); + if (i > b.end()) + { + throw UnmarshalOutOfBoundsException(__FILE__, __LINE__); + } + + if (_bigendian != ::IceInternal::bigendian) + { + reverse_copy(begin, i, reinterpret_cast<Byte*>(&v)); + } + else + { + copy(begin, i, reinterpret_cast<Byte*>(&v)); + } +} + +void +IceInternal::Stream::read(vector<Int>& v) +{ + Int sz; + read(sz); + + Container::iterator begin = i; + i += sz * sizeof(Int); + if (i > b.end()) + { + throw UnmarshalOutOfBoundsException(__FILE__, __LINE__); + } + + v.resize(sz); + if (_bigendian != ::IceInternal::bigendian) + { + for (int j = 0 ; j < sz ; ++j) + { + reverse_copy(begin, begin + sizeof(Int), reinterpret_cast<Byte*>(&v[j])); + begin += sizeof(Int); + } + } + else + { + copy(begin, i, reinterpret_cast<Byte*>(v.begin())); + } +} + +void +IceInternal::Stream::write(Long v) +{ + int pos = b.size(); + resize(pos + sizeof(Long)); + const Byte* p = reinterpret_cast<const Byte*>(&v); + copy(p, p + sizeof(Long), b.begin() + pos); +} + +void +IceInternal::Stream::write(const vector<Long>& v) +{ + int pos = b.size(); + Int sz = v.size(); + resize(pos + sizeof(Int) + sz * sizeof(Long)); + const Byte* p = reinterpret_cast<const Byte*>(&sz); + copy(p, p + sizeof(Int), b.begin() + pos); + p = reinterpret_cast<const Byte*>(v.begin()); + copy(p, p + sz * sizeof(Long), b.begin() + pos + sizeof(Int)); +} + +void +IceInternal::Stream::read(Long& v) +{ + Container::iterator begin = i; + i += sizeof(Long); + if (i > b.end()) + { + throw UnmarshalOutOfBoundsException(__FILE__, __LINE__); + } + + if (_bigendian != ::IceInternal::bigendian) + { + reverse_copy(begin, i, reinterpret_cast<Byte*>(&v)); + } + else + { + copy(begin, i, reinterpret_cast<Byte*>(&v)); + } +} + +void +IceInternal::Stream::read(vector<Long>& v) +{ + Int sz; + read(sz); + + Container::iterator begin = i; + i += sz * sizeof(Long); + if (i > b.end()) + { + throw UnmarshalOutOfBoundsException(__FILE__, __LINE__); + } + + v.resize(sz); + if (_bigendian != ::IceInternal::bigendian) + { + for (int j = 0 ; j < sz ; ++j) + { + reverse_copy(begin, begin + sizeof(Long), reinterpret_cast<Byte*>(&v[j])); + begin += sizeof(Long); + } + } + else + { + copy(begin, i, reinterpret_cast<Byte*>(v.begin())); + } +} + +void +IceInternal::Stream::write(Float v) +{ + int pos = b.size(); + resize(pos + sizeof(Float)); + const Byte* p = reinterpret_cast<const Byte*>(&v); + copy(p, p + sizeof(Float), b.begin() + pos); +} + +void +IceInternal::Stream::write(const vector<Float>& v) +{ + int pos = b.size(); + Int sz = v.size(); + resize(pos + sizeof(Int) + sz * sizeof(Float)); + const Byte* p = reinterpret_cast<const Byte*>(&sz); + copy(p, p + sizeof(Int), b.begin() + pos); + p = reinterpret_cast<const Byte*>(v.begin()); + copy(p, p + sz * sizeof(Float), b.begin() + pos + sizeof(Int)); +} + +void +IceInternal::Stream::read(Float& v) +{ + Container::iterator begin = i; + i += sizeof(Float); + if (i > b.end()) + { + throw UnmarshalOutOfBoundsException(__FILE__, __LINE__); + } + + if (_bigendian != ::IceInternal::bigendian) + { + reverse_copy(begin, i, reinterpret_cast<Byte*>(&v)); + } + else + { + copy(begin, i, reinterpret_cast<Byte*>(&v)); + } +} + +void +IceInternal::Stream::read(vector<Float>& v) +{ + Int sz; + read(sz); + + Container::iterator begin = i; + i += sz * sizeof(Float); + if (i > b.end()) + { + throw UnmarshalOutOfBoundsException(__FILE__, __LINE__); + } + + v.resize(sz); + if (_bigendian != ::IceInternal::bigendian) + { + for (int j = 0 ; j < sz ; ++j) + { + reverse_copy(begin, begin + sizeof(Float), reinterpret_cast<Byte*>(&v[j])); + begin += sizeof(Float); + } + } + else + { + copy(begin, i, reinterpret_cast<Byte*>(v.begin())); + } +} + +void +IceInternal::Stream::write(Double v) +{ + int pos = b.size(); + resize(pos + sizeof(Double)); + const Byte* p = reinterpret_cast<const Byte*>(&v); + copy(p, p + sizeof(Double), b.begin() + pos); +} + +void +IceInternal::Stream::write(const vector<Double>& v) +{ + int pos = b.size(); + Int sz = v.size(); + resize(pos + sizeof(Int) + sz * sizeof(Double)); + const Byte* p = reinterpret_cast<const Byte*>(&sz); + copy(p, p + sizeof(Int), b.begin() + pos); + p = reinterpret_cast<const Byte*>(v.begin()); + copy(p, p + sz * sizeof(Double), b.begin() + pos + sizeof(Int)); +} + +void +IceInternal::Stream::read(Double& v) +{ + Container::iterator begin = i; + i += sizeof(Double); + if (i > b.end()) + { + throw UnmarshalOutOfBoundsException(__FILE__, __LINE__); + } + + if (_bigendian != ::IceInternal::bigendian) + { + reverse_copy(begin, i, reinterpret_cast<Byte*>(&v)); + } + else + { + copy(begin, i, reinterpret_cast<Byte*>(&v)); + } +} + +void +IceInternal::Stream::read(vector<Double>& v) +{ + Int sz; + read(sz); + + Container::iterator begin = i; + i += sz * sizeof(Double); + if (i > b.end()) + { + throw UnmarshalOutOfBoundsException(__FILE__, __LINE__); + } + + v.resize(sz); + if (_bigendian != ::IceInternal::bigendian) + { + for (int j = 0 ; j < sz ; ++j) + { + reverse_copy(begin, begin + sizeof(Double), reinterpret_cast<Byte*>(&v[j])); + begin += sizeof(Double); + } + } + else + { + copy(begin, i, reinterpret_cast<Byte*>(v.begin())); + } +} + +void +IceInternal::Stream::write(const string& v) +{ + pair<multiset<int, CmpPosPos>::const_iterator, multiset<int, CmpPosPos>::const_iterator> p = + equal_range(_stringSet.begin(), _stringSet.end(), v, CmpPosString(b)); + if (p.first != p.second) + { + write(stringEncodingRedirect); + Int diff = b.size() - *p.first; + write(diff); + } + else + { + write(stringEncodingNormal); + int pos = b.size(); + resize(pos + v.size() + 1); + copy(v.begin(), v.end(), b.begin() + pos); + b.back() = 0; + _stringSet.insert(pos); + } +} + +void +IceInternal::Stream::write(const char* v) +{ + write(stringEncodingNormal); + int pos = b.size(); + int len = strlen(v); + resize(pos + len + 1); + copy(v, v + len + 1, b.begin() + pos); + _stringSet.insert(pos); +} + +void +IceInternal::Stream::write(const vector<string>& v) +{ + write(Ice::Int(v.size())); + vector<string>::const_iterator p; + for (p = v.begin(); p != v.end(); ++p) + { + write(*p); + } +} + +void +IceInternal::Stream::read(string& v) +{ + Byte stringEnc; + read(stringEnc); + + switch (stringEnc) + { + case stringEncodingNormal: + { + Container::iterator begin = i; + do + { + if (i >= b.end()) + { + throw UnmarshalOutOfBoundsException(__FILE__, __LINE__); + } + } + while (*i++); + v = begin; + _stringSet.insert(begin - b.begin()); + break; + } + + case stringEncodingRedirect: + { + Int diff; + read(diff); + Container::iterator j = i - 4 - diff; + Container::iterator begin = j; + if (j < b.begin()) + { + throw UnmarshalOutOfBoundsException(__FILE__, __LINE__); + } + + do + { + if (j >= b.end()) + { + throw UnmarshalOutOfBoundsException(__FILE__, __LINE__); + } + } + while (*j++); + v = begin; + break; + } + + default: + { + throw StringEncodingException(__FILE__, __LINE__); + } + } +} + +void +IceInternal::Stream::read(vector<string>& v) +{ + Ice::Int sz; + read(sz); + // Don't use v.resize(sz) or v.reserve(sz) here, as it cannot be + // checked whether sz is a reasonable value + while (sz--) + { +#ifdef WIN32 // STLBUG + v.push_back(string()); +#else + v.push_back(); +#endif + read(v.back()); + } +} + +void +IceInternal::Stream::write(const wstring& v) +{ + write(stringEncodingNormal); + wstring::const_iterator p; + for (p = v.begin(); p != v.end(); ++p) + { + write(static_cast<Short>(*p)); + } + write(Short(0)); +} + +void +IceInternal::Stream::write(const vector<wstring>& v) +{ + write(Ice::Int(v.size())); + vector<wstring>::const_iterator p; + for (p = v.begin(); p != v.end(); ++p) + { + write(*p); + } +} + +void +IceInternal::Stream::read(wstring& v) +{ + Byte stringEnc; + read(stringEnc); + if (stringEnc != stringEncodingNormal) + { + throw StringEncodingException(__FILE__, __LINE__); + } + + // TODO: This can be optimized + while (true) + { + Short s; + read(s); + if (!s) + break; + v += static_cast<wchar_t>(s); + } +} + +void +IceInternal::Stream::read(vector<wstring>& v) +{ + Ice::Int sz; + read(sz); + // Don't use v.resize(sz) or v.reserve(sz) here, as it cannot be + // checked whether sz is a reasonable value + while (sz--) + { +#ifdef WIN32 // STLBUG + v.push_back(wstring()); +#else + v.push_back(); +#endif + read(v.back()); + } +} + +void +IceInternal::Stream::write(const ObjectPtr& v) +{ + const string* classIds = v->_classIds(); + Ice::Int sz = 0; + while (classIds[sz] != "::Ice::Object") + { + ++sz; + } + write(sz); + for (int i = 0; i < sz; i++) + { + write(classIds[i]); + } + v->__write(this); +} + +void +IceInternal::Stream::read(ObjectPtr& v, const string& signatureType) +{ + vector<string> classIds; + read(classIds); + classIds.push_back("::Ice::Object"); + vector<string>::const_iterator p; + for (p = classIds.begin(); p != classIds.end(); ++p) + { + ValueFactoryPtr factory = _instance->valueFactoryManager()->lookup(*p); + + if (factory) + { + v = factory->create(*p); + v->__read(this); + + for (; p != classIds.end(); ++p) + { + if (*p == signatureType) + { + return; + } + } + + throw ValueUnmarshalException(__FILE__, __LINE__); + } + + if (*p == signatureType) + { + return; + } + + skipEncaps(); + } + + throw ValueUnmarshalException(__FILE__, __LINE__); +} + +IceInternal::Stream::CmpPosPos::CmpPosPos(const Container& cont) : + _cont(cont) +{ +} + +bool +IceInternal::Stream::CmpPosPos::operator()(int p, int q) const +{ + return strcmp(_cont.begin() + p, _cont.begin() + q) < 0; +} + +IceInternal::Stream::CmpPosString::CmpPosString(const Container& cont) : + _cont(cont) +{ +} + +bool +IceInternal::Stream::CmpPosString::operator()(int i, const string& s) const +{ + return _cont.begin() + i < s; +} + +bool +IceInternal::Stream::CmpPosString::operator()(const string& s, int i) const +{ + return s < _cont.begin() + i; +} diff --git a/cpp/src/Ice/TcpAcceptor.cpp b/cpp/src/Ice/TcpAcceptor.cpp new file mode 100644 index 00000000000..779551b2aee --- /dev/null +++ b/cpp/src/Ice/TcpAcceptor.cpp @@ -0,0 +1,151 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/TcpAcceptor.h> +#include <Ice/TcpTransceiver.h> +#include <Ice/Instance.h> +#include <Ice/TraceLevels.h> +#include <Ice/Logger.h> +#include <Ice/Network.h> +#include <Ice/LocalException.h> +#include <sstream> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +int +IceInternal::TcpAcceptor::fd() +{ + return _fd; +} + +void +IceInternal::TcpAcceptor::close() +{ +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 1) + { + ostringstream s; + s << "stopping to accept connections at " << toString(); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + + int fd = _fd; + _fd = INVALID_SOCKET; + closeSocket(fd); +} + +void +IceInternal::TcpAcceptor::shutdown() +{ +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 2) + { + ostringstream s; + s << "shutting down accepting connections at " << toString(); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + + ::shutdown(_fd, SHUT_RD); // Shutdown socket for reading +} + +void +IceInternal::TcpAcceptor::listen() +{ + try + { + doListen(_fd, _backlog); + } + catch(...) + { + _fd = INVALID_SOCKET; + throw; + } + +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 1) + { + ostringstream s; + s << "accepting connections at " << toString(); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif +} + +TransceiverPtr +IceInternal::TcpAcceptor::accept(int timeout) +{ + int fd = doAccept(_fd, timeout); +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 1) + { + ostringstream s; + s << "accepted connection\n" << fdToString(fd); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + return new TcpTransceiver(_instance, fd); +} + +string +IceInternal::TcpAcceptor::toString() const +{ + return addrToString(_addr); +} + +bool +IceInternal::TcpAcceptor::equivalent(const string& host, int port) const +{ + struct sockaddr_in addr; + getAddress(host.c_str(), port, addr); + if (addr.sin_addr.s_addr == htonl(INADDR_LOOPBACK)) + return port == ntohs(_addr.sin_port); + + struct sockaddr_in localAddr; + getLocalAddress(ntohs(_addr.sin_port), localAddr); + return memcmp(&addr, &localAddr, sizeof(struct sockaddr_in)) == 0; +} + +IceInternal::TcpAcceptor::TcpAcceptor(const InstancePtr& instance, int port) : + _instance(instance), + _backlog(0) +{ +#ifndef ICE_NO_TRACE + _traceLevels = _instance->traceLevels(); + _logger = _instance->logger(); +#endif + + if (_backlog <= 0) + _backlog = 5; + + try + { + memset(&_addr, 0, sizeof(_addr)); + _addr.sin_family = AF_INET; + _addr.sin_port = htons(port); + _addr.sin_addr.s_addr = htonl(INADDR_ANY); + + _fd = createSocket(false); + doBind(_fd, _addr); + } + catch(...) + { + _fd = INVALID_SOCKET; + throw; + } +} + +IceInternal::TcpAcceptor::~TcpAcceptor() +{ + assert(_fd == INVALID_SOCKET); +} diff --git a/cpp/src/Ice/TcpAcceptor.h b/cpp/src/Ice/TcpAcceptor.h new file mode 100644 index 00000000000..6a6a01f933d --- /dev/null +++ b/cpp/src/Ice/TcpAcceptor.h @@ -0,0 +1,60 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_TCP_ACCEPTOR_H +#define ICE_TCP_ACCEPTOR_H + +#include <Ice/TransceiverF.h> +#include <Ice/InstanceF.h> +#include <Ice/TraceLevelsF.h> +#include <Ice/LoggerF.h> +#include <Ice/Acceptor.h> + +#ifndef WIN32 +# include <netinet/in.h> // For struct sockaddr_in +#endif + +namespace IceInternal +{ + +class TcpEndpoint; + +class TcpAcceptor : public Acceptor +{ +public: + + virtual int fd(); + virtual void close(); + virtual void shutdown(); + virtual void listen(); + virtual TransceiverPtr accept(int); + virtual std::string toString() const; + + virtual bool equivalent(const std::string&, int) const; + +private: + + TcpAcceptor(const InstancePtr&, int); + virtual ~TcpAcceptor(); + friend class TcpEndpoint; + + InstancePtr _instance; + int _fd; + int _backlog; + struct sockaddr_in _addr; +#ifndef ICE_NO_TRACE + TraceLevelsPtr _traceLevels; + ::Ice::LoggerPtr _logger; +#endif +}; + +} + +#endif diff --git a/cpp/src/Ice/TcpConnector.cpp b/cpp/src/Ice/TcpConnector.cpp new file mode 100644 index 00000000000..3e595be4bc4 --- /dev/null +++ b/cpp/src/Ice/TcpConnector.cpp @@ -0,0 +1,70 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/TcpConnector.h> +#include <Ice/TcpTransceiver.h> +#include <Ice/Instance.h> +#include <Ice/TraceLevels.h> +#include <Ice/Logger.h> +#include <Ice/Network.h> +#include <Ice/LocalException.h> +#include <sstream> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +TransceiverPtr +IceInternal::TcpConnector::connect(int timeout) +{ +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 2) + { + ostringstream s; + s << "trying to connect to " << toString(); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + + int fd = createSocket(false); + doConnect(fd, _addr, timeout); + +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 1) + { + ostringstream s; + s << "connection established\n" << fdToString(fd); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + + return new TcpTransceiver(_instance, fd); +} + +string +IceInternal::TcpConnector::toString() const +{ + return addrToString(_addr); +} + +IceInternal::TcpConnector::TcpConnector(const InstancePtr& instance, const string& host, int port) : + _instance(instance) +{ +#ifndef ICE_NO_TRACE + _traceLevels = _instance->traceLevels(); + _logger = _instance->logger(); +#endif + + getAddress(host.c_str(), port, _addr); +} + +IceInternal::TcpConnector::~TcpConnector() +{ +} diff --git a/cpp/src/Ice/TcpConnector.h b/cpp/src/Ice/TcpConnector.h new file mode 100644 index 00000000000..1654d2b7ebe --- /dev/null +++ b/cpp/src/Ice/TcpConnector.h @@ -0,0 +1,52 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_TCP_CONNECTOR_H +#define ICE_TCP_CONNECTOR_H + +#include <Ice/TransceiverF.h> +#include <Ice/InstanceF.h> +#include <Ice/TraceLevelsF.h> +#include <Ice/LoggerF.h> +#include <Ice/Connector.h> + +#ifndef WIN32 +# include <netinet/in.h> // For struct sockaddr_in +#endif + +namespace IceInternal +{ + +class TcpEndpoint; + +class TcpConnector : public Connector +{ +public: + + virtual TransceiverPtr connect(int); + virtual std::string toString() const; + +private: + + TcpConnector(const InstancePtr&, const std::string&, int); + virtual ~TcpConnector(); + friend class TcpEndpoint; + + InstancePtr _instance; + struct sockaddr_in _addr; +#ifndef ICE_NO_TRACE + TraceLevelsPtr _traceLevels; + ::Ice::LoggerPtr _logger; +#endif +}; + +} + +#endif diff --git a/cpp/src/Ice/TcpTransceiver.cpp b/cpp/src/Ice/TcpTransceiver.cpp new file mode 100644 index 00000000000..55240ec8eb1 --- /dev/null +++ b/cpp/src/Ice/TcpTransceiver.cpp @@ -0,0 +1,263 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/TcpTransceiver.h> +#include <Ice/Instance.h> +#include <Ice/TraceLevels.h> +#include <Ice/Logger.h> +#include <Ice/Buffer.h> +#include <Ice/Network.h> +#include <Ice/LocalException.h> +#include <sstream> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +int +IceInternal::TcpTransceiver::fd() +{ + return _fd; +} + +void +IceInternal::TcpTransceiver::close() +{ +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 1) + { + ostringstream s; + s << "closing connection\n" << toString(); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + + int fd = _fd; + _fd = INVALID_SOCKET; + ::shutdown(fd, SHUT_RDWR); // helps to unblock threads in recv() + closeSocket(fd); +} + +void +IceInternal::TcpTransceiver::shutdown() +{ +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 2) + { + ostringstream s; + s << "shutting down connection\n" << toString(); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + + ::shutdown(_fd, SHUT_WR); // Shutdown socket for writing +} + +void +IceInternal::TcpTransceiver::write(Buffer& buf, int timeout) +{ + int packetSize = buf.b.end() - buf.i; + +#ifdef WIN32 + // + // Limit packet size to avoid performance problems on WIN32 + // + if (packetSize > 64 * 1024) + packetSize = 64 * 1024; +#endif + + while (buf.i != buf.b.end()) + { + int ret = ::send(_fd, buf.i, packetSize, 0); + + if (ret == 0) + { +#ifdef WIN32 + WSASetLastError(0); +#else + errno = 0; +#endif + throw ConnectionLostException(__FILE__, __LINE__); + } + + if (ret == SOCKET_ERROR) + { + if (interrupted()) + continue; + + if (noBuffers() && packetSize > 1024) + { + packetSize /= 2; + continue; + } + + if (wouldBlock()) + { + int fd = _fd; // Copy fd, in case another thread calls close() + if (fd != -1) + { + repeatSelect: + int ret; + FD_SET(fd, &wFdSet); + if (timeout >= 0) + { + struct timeval tv; + tv.tv_sec = timeout / 1000; + tv.tv_usec = (timeout - tv.tv_sec * 1000) * 1000; + ret = ::select(fd + 1, 0, &wFdSet, 0, &tv); + } + else + ret = ::select(fd + 1, 0, &wFdSet, 0, 0); + + if (ret == SOCKET_ERROR) + { + if (interrupted()) + goto repeatSelect; + + throw SocketException(__FILE__, __LINE__); + } + + if (ret == 0) + throw TimeoutException(__FILE__, __LINE__); + } + + continue; + } + + if (connectionLost()) + throw ConnectionLostException(__FILE__, __LINE__); + else + throw SocketException(__FILE__, __LINE__); + } + +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 3) + { + ostringstream s; + s << "sent " << ret << " of " << packetSize << " bytes via TCP\n" << toString(); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + + buf.i += ret; + + if (packetSize > buf.b.end() - buf.i) + packetSize = buf.b.end() - buf.i; + } +} + +void +IceInternal::TcpTransceiver::read(Buffer& buf, int timeout) +{ + int packetSize = buf.b.end() - buf.i; + + while (buf.i != buf.b.end()) + { + int ret = ::recv(_fd, buf.i, packetSize, 0); + + if (ret == 0) + { +#ifdef WIN32 + WSASetLastError(0); +#else + errno = 0; +#endif + throw ConnectionLostException(__FILE__, __LINE__); + } + + if (ret == SOCKET_ERROR) + { + if (interrupted()) + continue; + + if (noBuffers() && packetSize > 1024) + { + packetSize /= 2; + continue; + } + + if (wouldBlock()) + { + int fd = _fd; // Copy fd, in case another thread calls close() + if (fd != -1) + { + repeatSelect: + int ret; + FD_SET(fd, &rFdSet); + if (timeout >= 0) + { + struct timeval tv; + tv.tv_sec = timeout / 1000; + tv.tv_usec = (timeout - tv.tv_sec * 1000) * 1000; + ret = ::select(fd + 1, &rFdSet, 0, 0, &tv); + } + else + ret = ::select(fd + 1, &rFdSet, 0, 0, 0); + + if (ret == SOCKET_ERROR) + { + if (interrupted()) + goto repeatSelect; + + throw SocketException(__FILE__, __LINE__); + } + + if (ret == 0) + throw TimeoutException(__FILE__, __LINE__); + } + + continue; + } + + if (connectionLost()) + throw ConnectionLostException(__FILE__, __LINE__); + else + throw SocketException(__FILE__, __LINE__); + } + +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 3) + { + ostringstream s; + s << "received " << ret << " of " << packetSize << " bytes via TCP\n" << toString(); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + + buf.i += ret; + + if (packetSize > buf.b.end() - buf.i) + packetSize = buf.b.end() - buf.i; + } +} + +string +IceInternal::TcpTransceiver::toString() const +{ + return fdToString(_fd); +} + +IceInternal::TcpTransceiver::TcpTransceiver(const InstancePtr& instance, int fd) : + _instance(instance), + _fd(fd) +{ + FD_ZERO(&rFdSet); + FD_ZERO(&wFdSet); + +#ifndef ICE_NO_TRACE + _traceLevels = _instance->traceLevels(); + _logger = _instance->logger(); +#endif +} + +IceInternal::TcpTransceiver::~TcpTransceiver() +{ + assert(_fd == INVALID_SOCKET); +} diff --git a/cpp/src/Ice/TcpTransceiver.h b/cpp/src/Ice/TcpTransceiver.h new file mode 100644 index 00000000000..e60fca35de9 --- /dev/null +++ b/cpp/src/Ice/TcpTransceiver.h @@ -0,0 +1,55 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_TCP_TRANSCEIVER_H +#define ICE_TCP_TRANSCEIVER_H + +#include <Ice/InstanceF.h> +#include <Ice/TraceLevelsF.h> +#include <Ice/LoggerF.h> +#include <Ice/Transceiver.h> + +namespace IceInternal +{ + +class TcpConnector; +class TcpAcceptor; + +class TcpTransceiver : public Transceiver +{ +public: + + virtual int fd(); + virtual void close(); + virtual void shutdown(); + virtual void write(Buffer&, int); + virtual void read(Buffer&, int); + virtual std::string toString() const; + +private: + + TcpTransceiver(const InstancePtr&, int); + virtual ~TcpTransceiver(); + friend class TcpConnector; + friend class TcpAcceptor; + + InstancePtr _instance; + int _fd; + fd_set rFdSet; + fd_set wFdSet; +#ifndef ICE_NO_TRACE + TraceLevelsPtr _traceLevels; + ::Ice::LoggerPtr _logger; +#endif +}; + +} + +#endif diff --git a/cpp/src/Ice/ThreadPool.cpp b/cpp/src/Ice/ThreadPool.cpp new file mode 100644 index 00000000000..014311c8c2f --- /dev/null +++ b/cpp/src/Ice/ThreadPool.cpp @@ -0,0 +1,388 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/ThreadPool.h> +#include <Ice/EventHandler.h> +#include <Ice/Network.h> +#include <Ice/LocalException.h> +#include <Ice/Instance.h> +#include <Ice/Properties.h> +#include <Ice/Functional.h> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +void IceInternal::incRef(ThreadPool* p) { p->__incRef(); } +void IceInternal::decRef(ThreadPool* p) { p->__decRef(); } + +void +IceInternal::ThreadPool::_register(int fd, const EventHandlerPtr& handler) +{ + JTCSyncT<JTCMonitorT<JTCMutex> > sync(*this); + if (handler->server()) + ++_servers; + _adds.push_back(make_pair(fd, handler)); + setInterrupt(); +} + +void +IceInternal::ThreadPool::unregister(int fd) +{ + JTCSyncT<JTCMonitorT<JTCMutex> > sync(*this); + _removes.push_back(fd); + setInterrupt(); +} + +void +IceInternal::ThreadPool::promoteFollower() +{ + _threadMutex.unlock(); +} + +void +IceInternal::ThreadPool::waitUntilServerFinished() +{ + JTCSyncT<JTCMonitorT<JTCMutex> > sync(*this); + + while (_servers > 0) + { + try + { + wait(); + } + catch(const JTCInterruptedException&) + { + } + } +} + +void +IceInternal::ThreadPool::waitUntilFinished() +{ + JTCSyncT<JTCMonitorT<JTCMutex> > sync(*this); + + while (_handlers.size() > 0) + { + try + { + wait(); + } + catch(const JTCInterruptedException&) + { + } + } +} + +void +IceInternal::ThreadPool::joinWithAllThreads() +{ + // + // _threads is immutable after the initial creation in the + // constructor, therefore no synchronization is + // needed. (Synchronization wouldn't be possible here anyway, + // because otherwise the other threads would never terminate.) + // + for (vector<JTCThreadHandle>::iterator p = _threads.begin(); p != _threads.end(); ++p) + { + (*p)->join(); + } +} + +IceInternal::ThreadPool::ThreadPool(const InstancePtr& instance) : + _instance(instance), + _lastFd(-1), + _servers(0) +{ + int fds[2]; + createPipe(fds); + _fdIntrRead = fds[0]; + _fdIntrWrite = fds[1]; + setBlock(_fdIntrRead, false); + + FD_ZERO(&_fdSet); + FD_SET(_fdIntrRead, &_fdSet); + _maxFd = _fdIntrRead; + + try + { + int threadNum = 10; + string value = _instance->properties()->getProperty("ice.thread_pool.size"); + if (!value.empty()) + { + threadNum = atoi(value.c_str()); + if (threadNum < 1) + threadNum = 1; + } + + for (int i = 0 ; i < threadNum ; ++i) + { + JTCThreadHandle thread = new EventHandlerThread(this); + thread->start(); + _threads.push_back(thread); + } + } + catch(const JTCException&) + { + destroy(); + throw; + } +} + +IceInternal::ThreadPool::~ThreadPool() +{ + assert(!_instance); + + closeSocket(_fdIntrWrite); + closeSocket(_fdIntrRead); +} + +void +IceInternal::ThreadPool::destroy() +{ + JTCSyncT<JTCMonitorT<JTCMutex> > sync(*this); + _instance = 0; + setInterrupt(); +} + +void +IceInternal::ThreadPool::clearInterrupt() +{ + char s[32]; // Clear up to 32 interrupts at once +#ifdef WIN32 + while (::recv(_fdIntrRead, s, 32, 0) == 32) + ; +#else + while (::read(_fdIntrRead, s, 32) == 32) + ; +#endif +} + +void +IceInternal::ThreadPool::setInterrupt() +{ + char c = 0; +#ifdef WIN32 + ::send(_fdIntrWrite, &c, 1, 0); +#else + ::write(_fdIntrWrite, &c, 1); +#endif +} + +void +IceInternal::ThreadPool::run() +{ + while (true) + { + _threadMutex.lock(); + + EventHandlerPtr handler; + InstancePtr instance; + + repeatSelect: + fd_set fdSet; + memcpy(&fdSet, &_fdSet, sizeof(fd_set)); + if (::select(_maxFd + 1, &fdSet, 0, 0, 0) == SOCKET_ERROR) + { + if (interrupted()) + goto repeatSelect; + + _threadMutex.unlock(); + throw SocketException(__FILE__, __LINE__); + } + + { + JTCSyncT<JTCMonitorT<JTCMutex> > sync(*this); + + instance = _instance; + + if (!instance) // Destroyed? + { + // + // Don't clear the interrupt fd if destroyed, so that + // the other threads exit as well + // + _threadMutex.unlock(); + return; + } + + if (FD_ISSET(_fdIntrRead, &fdSet)) // Clear interrupt + { + clearInterrupt(); +#ifdef WIN32 + FD_CLR(static_cast<u_int>(_fdIntrRead), &fdSet); +#else + FD_CLR(_fdIntrRead, &fdSet); +#endif + } + + bool again = false; + + if (!_adds.empty()) + { + // + // New handlers have been added + // + vector<pair<int, EventHandlerPtr> >::iterator p; + for (p = _adds.begin(); p != _adds.end(); ++p) + { + _handlers.insert(*p); + FD_SET(p->first, &_fdSet); + _maxFd = max(_maxFd, p->first); + } + _adds.clear(); + again = true; + } + + if (!_removes.empty()) + { + // + // Handlers are permanently removed + // + vector<int>::iterator p; + for (p = _removes.begin(); p != _removes.end(); ++p) + { + std::map<int, EventHandlerPtr>::iterator q = + _handlers.find(*p); + assert(q != _handlers.end()); +#ifdef WIN32 + FD_CLR(static_cast<u_int>(*p), &_fdSet); +#else + FD_CLR(*p, &_fdSet); +#endif + q->second->finished(); + if (q->second->server()) + --_servers; + _handlers.erase(q); + } + _removes.clear(); + _maxFd = _fdIntrRead; + if (!_handlers.empty()) + _maxFd = max(_maxFd, (--_handlers.end())->first); + again = true; + if (_handlers.empty() || _servers == 0) + notifyAll(); // For waitUntil...Finished() methods + } + + if (again) + goto repeatSelect; + + // + // Round robin for the filedescriptors + // + do + { + if (++_lastFd > _maxFd) + _lastFd = 0; + } + while (!FD_ISSET(_lastFd, &fdSet)); + + std::map<int, EventHandlerPtr>::iterator p = _handlers.find(_lastFd); + assert(p != _handlers.end()); + handler = p->second; + } + + // + // If the handler is "readable", try to read a message + // + Stream stream(instance); + if (handler->readable()) + { + try + { + read(handler); + } + catch(const TimeoutException&) // Expected + { + goto repeatSelect; + } + catch(const LocalException& ex) + { + handler->exception(ex); + goto repeatSelect; + } + + stream.swap(handler->_stream); + assert(stream.i == stream.b.end()); + } + + handler->message(stream); + } +} + +void +IceInternal::ThreadPool::read(const EventHandlerPtr& handler) +{ + Stream& stream = handler->_stream; + + if (stream.b.size() < 8) // Read header? + { + if (stream.b.size() == 0) + { + stream.b.resize(8); + stream.i = stream.b.begin(); + } + + handler->read(stream); + if (stream.i != stream.b.end()) + return; + } + + if (stream.b.size() >= 8) // Interpret header? + { + int pos = stream.i - stream.b.begin(); + stream.i = stream.b.begin(); + bool peerBigendian; + stream.read(peerBigendian); + stream.pushBigendian(peerBigendian); + Byte protVer; + stream.read(protVer); + if (protVer != 0) + throw UnsupportedProtocolException(__FILE__, __LINE__); + Byte encVer; + stream.read(encVer); + if (encVer != 0) + throw UnsupportedEncodingException(__FILE__, __LINE__); + Byte messageType; + stream.read(messageType); + Int size; + stream.read(size); + if (size > 1024 * 1024) // TODO: configurable + throw ::Ice::MemoryLimitException(__FILE__, __LINE__); + stream.b.resize(size); + stream.i = stream.b.begin() + pos; + } + + if (stream.b.size() > 8 && stream.i != stream.b.end()) + handler->read(stream); +} + +void +IceInternal::ThreadPool::EventHandlerThread::run() +{ + try + { + _pool->run(); + } + catch(const LocalException& ex) + { + cerr << ex << endl; + } + catch(const JTCException& ex) + { + cerr << ex << endl; + } + catch(...) + { + cerr << "unknown exception" << endl; + } + + _pool = 0; // Break cyclic dependency +} diff --git a/cpp/src/Ice/ThreadPool.h b/cpp/src/Ice/ThreadPool.h new file mode 100644 index 00000000000..71983722237 --- /dev/null +++ b/cpp/src/Ice/ThreadPool.h @@ -0,0 +1,78 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_THREAD_POOL_H +#define ICE_THREAD_POOL_H + +#include <Ice/ThreadPoolF.h> +#include <Ice/InstanceF.h> +#include <Ice/EventHandlerF.h> +#include <Ice/Shared.h> +#include <map> + +namespace IceInternal +{ + +class Stream; + +class ThreadPool : public Shared, public JTCMonitorT<JTCMutex> +{ +public: + + void _register(int, const EventHandlerPtr&); + void unregister(int); + void promoteFollower(); + void waitUntilServerFinished(); + void waitUntilFinished(); + void joinWithAllThreads(); + +private: + + ThreadPool(const InstancePtr&); + virtual ~ThreadPool(); + void destroy(); + friend class Instance; + + void clearInterrupt(); + void setInterrupt(); + + void run(); + void read(const EventHandlerPtr&); + + InstancePtr _instance; + int _lastFd; + int _maxFd; + int _fdIntrRead; + int _fdIntrWrite; + fd_set _fdSet; + std::vector<std::pair<int, EventHandlerPtr> > _adds; + std::vector<int> _removes; + std::map<int, EventHandlerPtr> _handlers; + int _servers; + JTCMutex _threadMutex; + + class EventHandlerThread : public JTCThread + { + public: + + EventHandlerThread(ThreadPoolPtr pool) : _pool(pool) { } + virtual void run(); + + private: + + ThreadPoolPtr _pool; + }; + friend class EventHandlerThread; + std::vector<JTCThreadHandle> _threads; +}; + +} + +#endif diff --git a/cpp/src/Ice/ThreadPoolF.h b/cpp/src/Ice/ThreadPoolF.h new file mode 100644 index 00000000000..f8b8018fdc5 --- /dev/null +++ b/cpp/src/Ice/ThreadPoolF.h @@ -0,0 +1,26 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_THREAD_POOL_F_H +#define ICE_THREAD_POOL_F_H + +#include <Ice/Handle.h> + +namespace IceInternal +{ + +class ThreadPool; +void incRef(ThreadPool*); +void decRef(ThreadPool*); +typedef IceInternal::Handle<ThreadPool> ThreadPoolPtr; + +} + +#endif diff --git a/cpp/src/Ice/TraceLevels.cpp b/cpp/src/Ice/TraceLevels.cpp new file mode 100644 index 00000000000..7e454ff7dc5 --- /dev/null +++ b/cpp/src/Ice/TraceLevels.cpp @@ -0,0 +1,47 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/TraceLevels.h> +#include <Ice/Properties.h> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +void IceInternal::incRef(TraceLevels* p) { p->__incRef(); } +void IceInternal::decRef(TraceLevels* p) { p->__decRef(); } + +IceInternal::TraceLevels::TraceLevels(const PropertiesPtr& properties) : + network(0), + networkCat("network"), + protocol(0), + protocolCat("protocol"), + retry(0), + retryCat("retry") +{ + string value; + const string keyBase = "ice.trace."; + + value = properties->getProperty(keyBase + networkCat); + if (!value.empty()) + const_cast<int&>(network) = atoi(value.c_str()); + + value = properties->getProperty(keyBase + protocolCat); + if (!value.empty()) + const_cast<int&>(protocol) = atoi(value.c_str()); + + value = properties->getProperty(keyBase + retryCat); + if (!value.empty()) + const_cast<int&>(retry) = atoi(value.c_str()); +} + +IceInternal::TraceLevels::~TraceLevels() +{ +} diff --git a/cpp/src/Ice/TraceLevels.h b/cpp/src/Ice/TraceLevels.h new file mode 100644 index 00000000000..f30e5442e77 --- /dev/null +++ b/cpp/src/Ice/TraceLevels.h @@ -0,0 +1,38 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_TRACE_LEVELS_H +#define ICE_TRACE_LEVELS_H + +#include <Ice/TraceLevelsF.h> +#include <Ice/PropertiesF.h> +#include <Ice/Shared.h> + +namespace IceInternal +{ + +class TraceLevels : public Shared +{ +public: + + TraceLevels(const ::Ice::PropertiesPtr&); + virtual ~TraceLevels(); + + const int network; + const char* networkCat; + const int protocol; + const char* protocolCat; + const int retry; + const char* retryCat; +}; + +} + +#endif diff --git a/cpp/src/Ice/TraceLevelsF.h b/cpp/src/Ice/TraceLevelsF.h new file mode 100644 index 00000000000..16b0f577126 --- /dev/null +++ b/cpp/src/Ice/TraceLevelsF.h @@ -0,0 +1,26 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_TRACE_LEVELS_F_H +#define ICE_TRACE_LEVELS_F_H + +#include <Ice/Handle.h> + +namespace IceInternal +{ + +class TraceLevels; +void incRef(TraceLevels*); +void decRef(TraceLevels*); +typedef IceInternal::Handle<TraceLevels> TraceLevelsPtr; + +} + +#endif diff --git a/cpp/src/Ice/TraceUtil.cpp b/cpp/src/Ice/TraceUtil.cpp new file mode 100644 index 00000000000..75bd6663d83 --- /dev/null +++ b/cpp/src/Ice/TraceUtil.cpp @@ -0,0 +1,108 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/TraceUtil.h> +#include <Ice/Instance.h> +#include <Ice/TraceLevels.h> +#include <Ice/Logger.h> +#include <Ice/Stream.h> +#include <sstream> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +static void +printHeader(ostream& s, Stream& stream) +{ + bool bigendian; + stream.read(bigendian); + s << "\nbigendian = " << boolalpha << bigendian; + Byte protVer; + stream.read(protVer); + s << "\nprotocol version = " << static_cast<int>(protVer); + Byte encVer; + stream.read(encVer); + s << "\nencoding version = " << static_cast<int>(encVer); + Byte type; + stream.read(type); + s << "\nmessage type = " << static_cast<int>(type); + Int size; + stream.read(size); + s << "\nmessage size = " << size; +} + +void +IceInternal::traceHeader(const char* heading, const Stream& str, const ::Ice::LoggerPtr& logger, + const TraceLevelsPtr& tl) +{ + if (tl->protocol >= 1) + { + Stream& stream = const_cast<Stream&>(str); + Stream::Container::iterator p = stream.i; + stream.i = stream.b.begin(); + ostringstream s; + s << heading; + printHeader(s, stream); + logger->trace(tl->protocolCat, s.str()); + stream.i = p; + } +} + +void +IceInternal::traceRequest(const char* heading, const Stream& str, const ::Ice::LoggerPtr& logger, + const TraceLevelsPtr& tl) +{ + if (tl->protocol >= 1) + { + Stream& stream = const_cast<Stream&>(str); + Stream::Container::iterator p = stream.i; + stream.i = stream.b.begin(); + ostringstream s; + s << heading; + printHeader(s, stream); + Int requestId; + stream.read(requestId); + s << "\nrequest id = " << requestId; + if (requestId == 0) + s << " (oneway)"; + string identity; + stream.read(identity); + s << "\nidentity = " << identity; + string operation; + stream.read(operation); + s << "\noperation name = " << operation; + logger->trace(tl->protocolCat, s.str()); + stream.i = p; + } +} + +void +IceInternal::traceReply(const char* heading, const Stream& str, const ::Ice::LoggerPtr& logger, + const TraceLevelsPtr& tl) +{ + if (tl->protocol >= 1) + { + Stream& stream = const_cast<Stream&>(str); + Stream::Container::iterator p = stream.i; + stream.i = stream.b.begin(); + ostringstream s; + s << heading; + printHeader(s, stream); + Int requestId; + stream.read(requestId); + s << "\nrequest id = " << requestId; + Byte status; + stream.read(status); + s << "\nreply status = " << static_cast<int>(status); + logger->trace(tl->protocolCat, s.str()); + stream.i = p; + } +} diff --git a/cpp/src/Ice/TraceUtil.h b/cpp/src/Ice/TraceUtil.h new file mode 100644 index 00000000000..7588d0ca71a --- /dev/null +++ b/cpp/src/Ice/TraceUtil.h @@ -0,0 +1,31 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_TRACE_UTIL_H +#define ICE_TRACE_UTIL_H + +#include <Ice/LoggerF.h> +#include <Ice/TraceLevelsF.h> + +namespace IceInternal +{ + +class Stream; + +void traceHeader(const char*, const Stream&, + const ::Ice::LoggerPtr&, const TraceLevelsPtr&); +void traceRequest(const char*, const Stream&, + const ::Ice::LoggerPtr&, const TraceLevelsPtr&); +void traceReply(const char*, const Stream&, + const ::Ice::LoggerPtr&, const TraceLevelsPtr&); + +} + +#endif diff --git a/cpp/src/Ice/Transceiver.cpp b/cpp/src/Ice/Transceiver.cpp new file mode 100644 index 00000000000..e5fe262d098 --- /dev/null +++ b/cpp/src/Ice/Transceiver.cpp @@ -0,0 +1,18 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/Transceiver.h> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +void IceInternal::incRef(Transceiver* p) { p->__incRef(); } +void IceInternal::decRef(Transceiver* p) { p->__decRef(); } diff --git a/cpp/src/Ice/Transceiver.h b/cpp/src/Ice/Transceiver.h new file mode 100644 index 00000000000..dc1b292034d --- /dev/null +++ b/cpp/src/Ice/Transceiver.h @@ -0,0 +1,41 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_TRANSCEIVER_H +#define ICE_TRANSCEIVER_H + +#include <Ice/TransceiverF.h> +#include <Ice/Shared.h> + +namespace IceInternal +{ + +class Buffer; + +class Transceiver : public Shared +{ +public: + + virtual int fd() = 0; + virtual void close() = 0; + virtual void shutdown() = 0; + virtual void write(Buffer&, int) = 0; + virtual void read(Buffer&, int) = 0; + virtual std::string toString() const = 0; + +protected: + + Transceiver() { } + virtual ~Transceiver() { } +}; + +} + +#endif diff --git a/cpp/src/Ice/TransceiverF.h b/cpp/src/Ice/TransceiverF.h new file mode 100644 index 00000000000..9f9c0639b82 --- /dev/null +++ b/cpp/src/Ice/TransceiverF.h @@ -0,0 +1,26 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_TRANSCEIVER_F_H +#define ICE_TRANSCEIVER_F_H + +#include <Ice/Handle.h> + +namespace IceInternal +{ + +class Transceiver; +void incRef(Transceiver*); +void decRef(Transceiver*); +typedef IceInternal::Handle<Transceiver> TransceiverPtr; + +} + +#endif diff --git a/cpp/src/Ice/UdpTransceiver.cpp b/cpp/src/Ice/UdpTransceiver.cpp new file mode 100644 index 00000000000..5ec525de5f3 --- /dev/null +++ b/cpp/src/Ice/UdpTransceiver.cpp @@ -0,0 +1,213 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/UdpTransceiver.h> +#include <Ice/Instance.h> +#include <Ice/TraceLevels.h> +#include <Ice/Logger.h> +#include <Ice/Buffer.h> +#include <Ice/Network.h> +#include <Ice/LocalException.h> +#include <sstream> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +int +IceInternal::UdpTransceiver::fd() +{ + return _fd; +} + +void +IceInternal::UdpTransceiver::close() +{ +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 1) + { + ostringstream s; + if (_sender) + s << "stopping to send packets to " << toString(); + else + s << "stopping to receive packets at " << toString(); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + + int fd = _fd; + _fd = INVALID_SOCKET; + closeSocket(fd); +} + +void +IceInternal::UdpTransceiver::shutdown() +{ +} + +void +IceInternal::UdpTransceiver::write(Buffer& buf, int) +{ + assert(_sender); + assert(buf.i == buf.b.begin()); + const int packetSize = 64 * 1024; // TODO: configurable + assert(packetSize >= static_cast<int>(buf.b.size())); // TODO: exception + +repeat: + int ret = ::send(_fd, buf.b.begin(), buf.b.size(), 0); + + if (ret == SOCKET_ERROR) + { + if (interrupted()) + goto repeat; + + throw SocketException(__FILE__, __LINE__); + } + +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 3) + { + ostringstream s; + s << "sent " << ret << " bytes via UDP to " << toString(); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + + assert(ret == static_cast<int>(buf.b.size())); + buf.i = buf.b.end(); +} + +void +IceInternal::UdpTransceiver::read(Buffer& buf, int) +{ + assert(!_sender); + assert(buf.i == buf.b.begin()); + const int packetSize = 64 * 1024; // TODO: configurable + assert(packetSize >= static_cast<int>(buf.b.size())); // TODO: exception + buf.b.resize(packetSize); + buf.i = buf.b.begin(); + +repeat: + int ret = ::recv(_fd, buf.b.begin(), packetSize, 0); + + if (ret == SOCKET_ERROR) + { + if (interrupted()) + goto repeat; + + throw SocketException(__FILE__, __LINE__); + } + +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 3) + { + ostringstream s; + s << "received " << ret << " bytes via UDP at " << toString(); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + + buf.b.resize(ret); + buf.i = buf.b.end(); +} + +string +IceInternal::UdpTransceiver::toString() const +{ + return addrToString(_addr); +} + +bool +IceInternal::UdpTransceiver::equivalent(const string& host, int port) const +{ + if (_sender) + return false; + + struct sockaddr_in addr; + getAddress(host.c_str(), port, addr); + if (addr.sin_addr.s_addr == htonl(INADDR_LOOPBACK)) + return port == ntohs(_addr.sin_port); + + struct sockaddr_in localAddr; + getLocalAddress(ntohs(_addr.sin_port), localAddr); + return memcmp(&addr, &localAddr, sizeof(struct sockaddr_in)) == 0; +} + +IceInternal::UdpTransceiver::UdpTransceiver(const InstancePtr& instance, const string& host, int port) : + _instance(instance), + _sender(true) +{ +#ifndef ICE_NO_TRACE + _traceLevels = _instance->traceLevels(); + _logger = _instance->logger(); +#endif + + try + { + getAddress(host.c_str(), port, _addr); + + _fd = createSocket(true); + doConnect(_fd, _addr, -1); + +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 1) + { + ostringstream s; + s << "starting to send packets to " << toString(); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + } + catch(...) + { + _fd = INVALID_SOCKET; + throw; + } +} + +IceInternal::UdpTransceiver::UdpTransceiver(const InstancePtr& instance, int port) : + _instance(instance), + _sender(false) +{ +#ifndef ICE_NO_TRACE + _traceLevels = _instance->traceLevels(); + _logger = _instance->logger(); +#endif + + try + { + memset(&_addr, 0, sizeof(_addr)); + _addr.sin_family = AF_INET; + _addr.sin_port = htons(port); + _addr.sin_addr.s_addr = htonl(INADDR_ANY); + + _fd = createSocket(true); + doBind(_fd, _addr); + +#ifndef ICE_NO_TRACE + if (_traceLevels->network >= 1) + { + ostringstream s; + s << "starting to receive packets at " << toString(); + _logger->trace(_traceLevels->networkCat, s.str()); + } +#endif + } + catch(...) + { + _fd = INVALID_SOCKET; + throw; + } +} + +IceInternal::UdpTransceiver::~UdpTransceiver() +{ + assert(_fd == INVALID_SOCKET); +} diff --git a/cpp/src/Ice/UdpTransceiver.h b/cpp/src/Ice/UdpTransceiver.h new file mode 100644 index 00000000000..5900edfcdc2 --- /dev/null +++ b/cpp/src/Ice/UdpTransceiver.h @@ -0,0 +1,60 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_UDP_TRANSCEIVER_H +#define ICE_UDP_TRANSCEIVER_H + +#include <Ice/InstanceF.h> +#include <Ice/TraceLevelsF.h> +#include <Ice/LoggerF.h> +#include <Ice/Transceiver.h> + +#ifndef WIN32 +# include <netinet/in.h> // For struct sockaddr_in +#endif + +namespace IceInternal +{ + +class UdpEndpoint; + +class UdpTransceiver : public Transceiver +{ +public: + + virtual int fd(); + virtual void close(); + virtual void shutdown(); + virtual void write(Buffer&, int); + virtual void read(Buffer&, int); + virtual std::string toString() const; + + virtual bool equivalent(const std::string&, int) const; + +private: + + UdpTransceiver(const InstancePtr&, const std::string&, int); + UdpTransceiver(const InstancePtr&, int); + virtual ~UdpTransceiver(); + friend class UdpEndpoint; + + InstancePtr _instance; + bool _sender; + int _fd; + struct sockaddr_in _addr; +#ifndef ICE_NO_TRACE + TraceLevelsPtr _traceLevels; + ::Ice::LoggerPtr _logger; +#endif +}; + +} + +#endif diff --git a/cpp/src/Ice/ValueFactoryManager.cpp b/cpp/src/Ice/ValueFactoryManager.cpp new file mode 100644 index 00000000000..40f87308957 --- /dev/null +++ b/cpp/src/Ice/ValueFactoryManager.cpp @@ -0,0 +1,49 @@ +// ********************************************************************** +// +// Copyright (c) 2001 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <Ice/ValueFactoryManager.h> +#include <Ice/ValueFactory.h> + +using namespace std; +using namespace Ice; +using namespace IceInternal; + +void IceInternal::incRef(ValueFactoryManager* p) { p->__incRef(); } +void IceInternal::decRef(ValueFactoryManager* p) { p->__decRef(); } + +void +IceInternal::ValueFactoryManager::install(const ValueFactoryPtr& factory, const string& id) +{ + JTCSyncT<JTCMutex> sync(*this); + _factories.insert(make_pair(id, factory)); +} + +ValueFactoryPtr +IceInternal::ValueFactoryManager::lookup(const string& id) +{ + JTCSyncT<JTCMutex> sync(*this); + map<string, ::Ice::ValueFactoryPtr>::const_iterator p; + p = _factories.find(id); + if (p != _factories.end()) + return p->second; + else + return 0; +} + +IceInternal::ValueFactoryManager::ValueFactoryManager() +{ +} + +void +IceInternal::ValueFactoryManager::destroy() +{ + JTCSyncT<JTCMutex> sync(*this); + _factories.clear(); +} diff --git a/cpp/src/Ice/ValueFactoryManager.h b/cpp/src/Ice/ValueFactoryManager.h new file mode 100644 index 00000000000..1246b866477 --- /dev/null +++ b/cpp/src/Ice/ValueFactoryManager.h @@ -0,0 +1,40 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_VALUE_FACTORY_MANAGER_H +#define ICE_VALUE_FACTORY_MANAGER_H + +#include <Ice/ValueFactoryManagerF.h> +#include <Ice/ValueFactoryF.h> +#include <Ice/Shared.h> +#include <map> + +namespace IceInternal +{ + +class ValueFactoryManager : public Shared, public JTCMutex +{ +public: + + void install(const ::Ice::ValueFactoryPtr&, const std::string&); + ::Ice::ValueFactoryPtr lookup(const std::string&); + +private: + + ValueFactoryManager(); + void destroy(); + friend class Instance; + + std::map<std::string, ::Ice::ValueFactoryPtr> _factories; +}; + +} + +#endif diff --git a/cpp/src/Ice/ValueFactoryManagerF.h b/cpp/src/Ice/ValueFactoryManagerF.h new file mode 100644 index 00000000000..2dd00c090e7 --- /dev/null +++ b/cpp/src/Ice/ValueFactoryManagerF.h @@ -0,0 +1,26 @@ +// ********************************************************************** +// +// Copyright (c) 2002 +// MutableRealms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#ifndef ICE_VALUE_FACTORY_MANAGER_F_H +#define ICE_VALUE_FACTORY_MANAGER_F_H + +#include <Ice/Handle.h> + +namespace IceInternal +{ + +class ValueFactoryManager; +void incRef(ValueFactoryManager*); +void decRef(ValueFactoryManager*); +typedef IceInternal::Handle<ValueFactoryManager> ValueFactoryManagerPtr; + +} + +#endif diff --git a/cpp/src/Ice/ice.dsp b/cpp/src/Ice/ice.dsp new file mode 100644 index 00000000000..33c813733e8 --- /dev/null +++ b/cpp/src/Ice/ice.dsp @@ -0,0 +1,1029 @@ +# Microsoft Developer Studio Project File - Name="Ice" - Package Owner=<4>
+# Microsoft Developer Studio Generated Build File, Format Version 6.00
+# ** DO NOT EDIT **
+
+# TARGTYPE "Win32 (x86) Dynamic-Link Library" 0x0102
+
+CFG=Ice - Win32 Debug
+!MESSAGE This is not a valid makefile. To build this project using NMAKE,
+!MESSAGE use the Export Makefile command and run
+!MESSAGE
+!MESSAGE NMAKE /f "Ice.mak".
+!MESSAGE
+!MESSAGE You can specify a configuration when running NMAKE
+!MESSAGE by defining the macro CFG on the command line. For example:
+!MESSAGE
+!MESSAGE NMAKE /f "Ice.mak" CFG="Ice - Win32 Debug"
+!MESSAGE
+!MESSAGE Possible choices for configuration are:
+!MESSAGE
+!MESSAGE "Ice - Win32 Release" (based on "Win32 (x86) Dynamic-Link Library")
+!MESSAGE "Ice - Win32 Debug" (based on "Win32 (x86) Dynamic-Link Library")
+!MESSAGE
+
+# Begin Project
+# PROP AllowPerConfigDependencies 0
+# PROP Scc_ProjName ""
+# PROP Scc_LocalPath ""
+CPP=cl.exe
+MTL=midl.exe
+RSC=rc.exe
+
+!IF "$(CFG)" == "Ice - Win32 Release"
+
+# PROP BASE Use_MFC 0
+# PROP BASE Use_Debug_Libraries 0
+# PROP BASE Output_Dir "Release"
+# PROP BASE Intermediate_Dir "Release"
+# PROP BASE Target_Dir ""
+# PROP Use_MFC 0
+# PROP Use_Debug_Libraries 0
+# PROP Output_Dir "Release"
+# PROP Intermediate_Dir "Release"
+# PROP Ignore_Export_Lib 0
+# PROP Target_Dir ""
+# ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "LIBRARY_EXPORTS" /Yu"stdafx.h" /FD /c
+# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I ".." /I "../../include" /D "NDEBUG" /D "WIN32" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "ICE_EXPORTS" /YX /FD /c
+# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32
+# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32
+# ADD BASE RSC /l 0x409 /d "NDEBUG"
+# ADD RSC /l 0x409 /d "NDEBUG"
+BSC32=bscmake.exe
+# ADD BASE BSC32 /nologo
+# ADD BSC32 /nologo
+LINK32=link.exe
+# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386
+# ADD LINK32 jtc.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib ws2_32.lib /nologo /dll /machine:I386 /out:"Release/ice001.dll"
+# SUBTRACT LINK32 /pdb:none
+# Begin Special Build Tool
+SOURCE="$(InputPath)"
+PostBuild_Cmds=copy Release\ice001.* ..\..\lib
+# End Special Build Tool
+
+!ELSEIF "$(CFG)" == "Ice - Win32 Debug"
+
+# PROP BASE Use_MFC 0
+# PROP BASE Use_Debug_Libraries 1
+# PROP BASE Output_Dir "Debug"
+# PROP BASE Intermediate_Dir "Debug"
+# PROP BASE Target_Dir ""
+# PROP Use_MFC 0
+# PROP Use_Debug_Libraries 1
+# PROP Output_Dir "Debug"
+# PROP Intermediate_Dir "Debug"
+# PROP Ignore_Export_Lib 0
+# PROP Target_Dir ""
+# ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "LIBRARY_EXPORTS" /Yu"stdafx.h" /FD /GZ /c
+# ADD CPP /nologo /MDd /W3 /Gm /GR /GX /ZI /Od /I ".." /I "../../include" /D "_DEBUG" /D "WIN32" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "ICE_EXPORTS" /YX /FD /GZ /c
+# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32
+# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32
+# ADD BASE RSC /l 0x409 /d "_DEBUG"
+# ADD RSC /l 0x409 /d "_DEBUG"
+BSC32=bscmake.exe
+# ADD BASE BSC32 /nologo
+# ADD BSC32 /nologo
+LINK32=link.exe
+# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept
+# ADD LINK32 jtcd.lib ws2_32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /out:"Debug/ice001d.dll" /pdbtype:sept
+# SUBTRACT LINK32 /pdb:none
+# Begin Special Build Tool
+SOURCE="$(InputPath)"
+PostBuild_Cmds=copy Debug\ice001d.* ..\..\lib
+# End Special Build Tool
+
+!ENDIF
+
+# Begin Target
+
+# Name "Ice - Win32 Release"
+# Name "Ice - Win32 Debug"
+# Begin Group "Source Files"
+
+# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat"
+# Begin Source File
+
+SOURCE=.\Acceptor.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\Collector.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\Communicator.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\CommunicatorI.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\Connector.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\Emitter.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\Endpoint.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\EventHandler.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\Incoming.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\Instance.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\LocalException.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\LocalObject.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\Logger.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\LoggerI.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\Network.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\Object.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\ObjectAdapter.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\ObjectAdapterFactory.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\ObjectAdapterI.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\Outgoing.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\Pickler.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\PicklerI.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\Properties.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\PropertiesI.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\Proxy.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\ProxyFactory.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\Reference.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\Shared.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\SslAcceptor.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\SslConnector.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\SslTransceiver.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\Stream.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\TcpAcceptor.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\TcpConnector.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\TcpTransceiver.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\ThreadPool.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\TraceLevels.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\TraceUtil.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\Transceiver.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\UdpTransceiver.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\ValueFactory.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\ValueFactoryManager.cpp
+# End Source File
+# End Group
+# Begin Group "Header Files"
+
+# PROP Default_Filter "h;hpp;hxx;hm;inl"
+# Begin Source File
+
+SOURCE=.\Ice\Acceptor.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\AcceptorF.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\Buffer.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\Collector.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\CollectorF.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\Communicator.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\CommunicatorF.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\CommunicatorI.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\Config.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\Connector.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\ConnectorF.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\Emitter.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\EmitterF.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\Endpoint.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\EndpointF.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\EventHandler.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\EventHandlerF.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\Functional.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\Handle.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\Ice.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\Incoming.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\Initialize.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\Instance.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\InstanceF.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\LocalException.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\LocalObject.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\LocalObjectF.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\Logger.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\LoggerF.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\LoggerI.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\Native.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\Network.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\Object.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\ObjectAdapter.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\ObjectAdapterF.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\ObjectAdapterFactory.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\ObjectAdapterFactoryF.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\ObjectAdapterI.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\ObjectF.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\Outgoing.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\Pickler.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\PicklerF.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\PicklerI.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\Properties.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\PropertiesF.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\PropertiesI.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\Proxy.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\ProxyF.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\ProxyFactory.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\ProxyFactoryF.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\ProxyHandle.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\Reference.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\ReferenceF.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\Shared.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\SslAcceptor.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\SslConnector.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\SslTransceiver.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\Stream.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\TcpAcceptor.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\TcpConnector.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\TcpTransceiver.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\ThreadPool.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\ThreadPoolF.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\TraceLevels.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\TraceLevelsF.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\TraceUtil.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\Transceiver.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\TransceiverF.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\UdpTransceiver.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\ValueFactory.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\include\Ice\ValueFactoryF.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\ValueFactoryManager.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Ice\ValueFactoryManagerF.h
+# End Source File
+# End Group
+# Begin Group "Resource Files"
+
+# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe"
+# Begin Source File
+
+SOURCE=..\..\slice\Ice\Communicator.ice
+
+!IF "$(CFG)" == "Ice - Win32 Release"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\Communicator.ice
+
+BuildCmds= \
+ set PATH=%PATH%;..\..\lib \
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/Communicator.ice \
+ move Communicator.h ..\..\include\Ice \
+
+
+"..\..\include\Ice\Communicator.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+
+"Communicator.cpp" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+# End Custom Build
+
+!ELSEIF "$(CFG)" == "Ice - Win32 Debug"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\Communicator.ice
+
+BuildCmds= \
+ set PATH=%PATH%;..\..\lib \
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/Communicator.ice \
+ move Communicator.h ..\..\include\Ice \
+
+
+"..\..\include\Ice\Communicator.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+
+"Communicator.cpp" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+# End Custom Build
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\slice\Ice\CommunicatorF.ice
+
+!IF "$(CFG)" == "Ice - Win32 Release"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\CommunicatorF.ice
+
+"..\..\include\Ice\CommunicatorF.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ set PATH=%PATH%;..\..\lib
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/CommunicatorF.ice
+ move CommunicatorF.h ..\..\include\Ice
+ del CommunicatorF.cpp
+
+# End Custom Build
+
+!ELSEIF "$(CFG)" == "Ice - Win32 Debug"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\CommunicatorF.ice
+
+"..\..\include\Ice\CommunicatorF.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ set PATH=%PATH%;..\..\lib
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/CommunicatorF.ice
+ move CommunicatorF.h ..\..\include\Ice
+ del CommunicatorF.cpp
+
+# End Custom Build
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\slice\Ice\Logger.ice
+
+!IF "$(CFG)" == "Ice - Win32 Release"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\Logger.ice
+
+BuildCmds= \
+ set PATH=%PATH%;..\..\lib \
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/Logger.ice \
+ move Logger.h ..\..\include\Ice \
+
+
+"..\..\include\Ice\Logger.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+
+"Logger.cpp" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+# End Custom Build
+
+!ELSEIF "$(CFG)" == "Ice - Win32 Debug"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\Logger.ice
+
+BuildCmds= \
+ set PATH=%PATH%;..\..\lib \
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/Logger.ice \
+ move Logger.h ..\..\include\Ice \
+
+
+"..\..\include\Ice\Logger.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+
+"Logger.cpp" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+# End Custom Build
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\slice\Ice\LoggerF.ice
+
+!IF "$(CFG)" == "Ice - Win32 Release"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\LoggerF.ice
+
+"..\..\include\Ice\LoggerF.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ set PATH=%PATH%;..\..\lib
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/LoggerF.ice
+ move LoggerF.h ..\..\include\Ice
+ del LoggerF.cpp
+
+# End Custom Build
+
+!ELSEIF "$(CFG)" == "Ice - Win32 Debug"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\LoggerF.ice
+
+"..\..\include\Ice\LoggerF.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ set PATH=%PATH%;..\..\lib
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/LoggerF.ice
+ move LoggerF.h ..\..\include\Ice
+ del LoggerF.cpp
+
+# End Custom Build
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\slice\Ice\ObjectAdapter.ice
+
+!IF "$(CFG)" == "Ice - Win32 Release"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\ObjectAdapter.ice
+
+BuildCmds= \
+ set PATH=%PATH%;..\..\lib \
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/ObjectAdapter.ice \
+ move ObjectAdapter.h ..\..\include\Ice \
+
+
+"..\..\include\Ice\ObjectAdapter.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+
+"ObjectAdapter.cpp" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+# End Custom Build
+
+!ELSEIF "$(CFG)" == "Ice - Win32 Debug"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\ObjectAdapter.ice
+
+BuildCmds= \
+ set PATH=%PATH%;..\..\lib \
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/ObjectAdapter.ice \
+ move ObjectAdapter.h ..\..\include\Ice \
+
+
+"..\..\include\Ice\ObjectAdapter.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+
+"ObjectAdapter.cpp" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+# End Custom Build
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\slice\Ice\ObjectAdapterF.ice
+
+!IF "$(CFG)" == "Ice - Win32 Release"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\ObjectAdapterF.ice
+
+"..\..\include\Ice\ObjectAdapterF.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ set PATH=%PATH%;..\..\lib
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/ObjectAdapterF.ice
+ move ObjectAdapterF.h ..\..\include\Ice
+ del ObjectAdapterF.cpp
+
+# End Custom Build
+
+!ELSEIF "$(CFG)" == "Ice - Win32 Debug"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\ObjectAdapterF.ice
+
+"..\..\include\Ice\ObjectAdapterF.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ set PATH=%PATH%;..\..\lib
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/ObjectAdapterF.ice
+ move ObjectAdapterF.h ..\..\include\Ice
+ del ObjectAdapterF.cpp
+
+# End Custom Build
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\slice\Ice\Pickler.ice
+
+!IF "$(CFG)" == "Ice - Win32 Release"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\Pickler.ice
+
+BuildCmds= \
+ set PATH=%PATH%;..\..\lib \
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/Pickler.ice \
+ move Pickler.h ..\..\include\Ice \
+
+
+"..\..\include\Ice\Pickler.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+
+"Pickler.cpp" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+# End Custom Build
+
+!ELSEIF "$(CFG)" == "Ice - Win32 Debug"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\Pickler.ice
+
+BuildCmds= \
+ set PATH=%PATH%;..\..\lib \
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/Pickler.ice \
+ move Pickler.h ..\..\include\Ice \
+
+
+"..\..\include\Ice\Pickler.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+
+"Pickler.cpp" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+# End Custom Build
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\slice\Ice\PicklerF.ice
+
+!IF "$(CFG)" == "Ice - Win32 Release"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\PicklerF.ice
+
+"..\..\include\Ice\PicklerF.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ set PATH=%PATH%;..\..\lib
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/PicklerF.ice
+ move PicklerF.h ..\..\include\Ice
+ del PicklerF.cpp
+
+# End Custom Build
+
+!ELSEIF "$(CFG)" == "Ice - Win32 Debug"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\PicklerF.ice
+
+"..\..\include\Ice\PicklerF.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ set PATH=%PATH%;..\..\lib
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/PicklerF.ice
+ move PicklerF.h ..\..\include\Ice
+ del PicklerF.cpp
+
+# End Custom Build
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\slice\Ice\Properties.ice
+
+!IF "$(CFG)" == "Ice - Win32 Release"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\Properties.ice
+
+BuildCmds= \
+ set PATH=%PATH%;..\..\lib \
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/Properties.ice \
+ move Properties.h ..\..\include\Ice \
+
+
+"..\..\include\Ice\Properties.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+
+"Properties.cpp" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+# End Custom Build
+
+!ELSEIF "$(CFG)" == "Ice - Win32 Debug"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\Properties.ice
+
+BuildCmds= \
+ set PATH=%PATH%;..\..\lib \
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/Properties.ice \
+ move Properties.h ..\..\include\Ice \
+
+
+"..\..\include\Ice\Properties.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+
+"Properties.cpp" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+# End Custom Build
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\slice\Ice\PropertiesF.ice
+
+!IF "$(CFG)" == "Ice - Win32 Release"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\PropertiesF.ice
+
+"..\..\include\Ice\PropertiesF.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ set PATH=%PATH%;..\..\lib
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/PropertiesF.ice
+ move PropertiesF.h ..\..\include\Ice
+ del PropertiesF.cpp
+
+# End Custom Build
+
+!ELSEIF "$(CFG)" == "Ice - Win32 Debug"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\PropertiesF.ice
+
+"..\..\include\Ice\PropertiesF.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ set PATH=%PATH%;..\..\lib
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/PropertiesF.ice
+ move PropertiesF.h ..\..\include\Ice
+ del PropertiesF.cpp
+
+# End Custom Build
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\slice\Ice\ValueFactory.ice
+
+!IF "$(CFG)" == "Ice - Win32 Release"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\ValueFactory.ice
+
+BuildCmds= \
+ set PATH=%PATH%;..\..\lib \
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/ValueFactory.ice \
+ move ValueFactory.h ..\..\include\Ice \
+
+
+"..\..\include\Ice\ValueFactory.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+
+"ValueFactory.cpp" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+# End Custom Build
+
+!ELSEIF "$(CFG)" == "Ice - Win32 Debug"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\ValueFactory.ice
+
+BuildCmds= \
+ set PATH=%PATH%;..\..\lib \
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/ValueFactory.ice \
+ move ValueFactory.h ..\..\include\Ice \
+
+
+"..\..\include\Ice\ValueFactory.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+
+"ValueFactory.cpp" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ $(BuildCmds)
+# End Custom Build
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\slice\Ice\ValueFactoryF.ice
+
+!IF "$(CFG)" == "Ice - Win32 Release"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\ValueFactoryF.ice
+
+"..\..\include\Ice\ValueFactoryF.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ set PATH=%PATH%;..\..\lib
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/ValueFactoryF.ice
+ move ValueFactoryF.h ..\..\include\Ice
+ del ValueFactoryF.cpp
+
+# End Custom Build
+
+!ELSEIF "$(CFG)" == "Ice - Win32 Debug"
+
+# Begin Custom Build
+InputPath=..\..\slice\Ice\ValueFactoryF.ice
+
+"..\..\include\Ice\ValueFactoryF.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ set PATH=%PATH%;..\..\lib
+ ..\..\bin\slice2cpp.exe --dll-export ICE_API --include-dir Ice -I../../slice ../../slice/Ice/ValueFactoryF.ice
+ move ValueFactoryF.h ..\..\include\Ice
+ del ValueFactoryF.cpp
+
+# End Custom Build
+
+!ENDIF
+
+# End Source File
+# End Group
+# End Target
+# End Project
diff --git a/cpp/src/Makefile b/cpp/src/Makefile index 6362e3b72a5..6af7be3cf62 100644 --- a/cpp/src/Makefile +++ b/cpp/src/Makefile @@ -12,7 +12,7 @@ top_srcdir = .. include $(top_srcdir)/config/Make.rules -SUBDIRS = slice library +SUBDIRS = slice Ice $(EVERYTHING):: @for subdir in $(SUBDIRS); \ diff --git a/cpp/src/Slice/Makefile b/cpp/src/Slice/Makefile index a3d9f9aa3b9..efdb97c94aa 100644 --- a/cpp/src/Slice/Makefile +++ b/cpp/src/Slice/Makefile @@ -29,6 +29,8 @@ SRCS = $(OBJS:.o=.cpp) include $(top_srcdir)/config/Make.rules +CPPFLAGS := -I. $(CPPFLAGS) + $(VERSIONED_NAME): $(OBJS) rm -f $@ $(CXX) $(CXXFLAGS) $(BASELDFLAGS) -shared -o $@ $(OBJS) diff --git a/cpp/src/slice2cpp/Gen.cpp b/cpp/src/slice2cpp/Gen.cpp index 9198e95c486..57206998170 100644 --- a/cpp/src/slice2cpp/Gen.cpp +++ b/cpp/src/slice2cpp/Gen.cpp @@ -1858,7 +1858,14 @@ Slice::Gen::HandleVisitor::visitClassDefStart(const ClassDefPtr& p) C << nl << "::Ice::ObjectPrx proxy;"; // TODO: Should be ::Ice::__read C << nl << "::IceInternal::read(__is, proxy);"; + C << nl << "if (!proxy)"; + C << sb; + C << nl << "v = 0;"; + C << eb; + C << nl << "else"; + C << sb; C << nl << "v = new ::IceProxy" << scoped << ';'; C << nl << "proxy->__copyTo(v.get());"; C << eb; + C << eb; } diff --git a/cpp/src/slice2cpp/Makefile b/cpp/src/slice2cpp/Makefile index e82b5ebeca3..4087295d345 100644 --- a/cpp/src/slice2cpp/Makefile +++ b/cpp/src/slice2cpp/Makefile @@ -22,7 +22,7 @@ SRCS = $(OBJS:.o=.cpp) include $(top_srcdir)/config/Make.rules -CPPFLAGS := -I../parser $(CPPFLAGS) +CPPFLAGS := -I. -I../parser $(CPPFLAGS) $(NAME): $(OBJS) rm -f $@ diff --git a/cpp/src/slice2docbook/Makefile b/cpp/src/slice2docbook/Makefile index 0eadcdb814d..e52cf8d0289 100644 --- a/cpp/src/slice2docbook/Makefile +++ b/cpp/src/slice2docbook/Makefile @@ -22,7 +22,7 @@ SRCS = $(OBJS:.o=.cpp) include $(top_srcdir)/config/Make.rules -CPPFLAGS := -I../parser $(CPPFLAGS) +CPPFLAGS := -I. -I../parser $(CPPFLAGS) $(NAME): $(OBJS) rm -f $@ |