As described in the options documentation, various components in TAO can be customized by specifying options for those components. This document illustrates how to combine these options in order to affect the behavior and performance of a TAO ORB, particularly its concurrency model.
TAO configures itself using the ACE Service Configurator framework. Thus, options are specified in the familiar svc.conf file (if you want to use a different file name, use the -ORBSvcConf option). You can also setup default configurations for your programs. Please see the Programming Considerations for more detailed discussion on this.
Details for the following configurations are provided.
- Configurating key components:
- Server Concurrency Strategy.
- Number of ORBs.
- POA.
- Collocation Table.
- Forwarding Profile
- orbsvcs Library
- Configuration examples
- Single-threaded, reactive model.
- Multiple threads, single ORB, thread-per-connection model.
- Multiple threads, single ORB, TAO thread-pool model.
- Multiple threads, single ORB, Real-time CORBA thread-pool model.
- Multiple threads, multiple ORBs, reactive model.
- Multiple threads, multiple ORBs, thread-per-connection model.
- Multiple threads, ORB-per-thread, thread-pool reactive model.
- Each configuration has the following information:
Typical Use A brief description of the scenario and its typical use. Number of Threads The number of threads used by ORB-related activities. Thread Creator Identifies the creator of the threads discussed above. Thread task Describes what task is undertaken for each thread. Options Specifies the options for each service in order to utilize this configuration. - Programming Considerations
- Configuration for Homogenous Systems
- Configuration Suggestions
Server_Strategy_Factory
entry of the svc.conf
file. This
specifies the concurrency strategy an ORB uses. This strategy
is orthogonal the the number of ORBs or threads that are
configured in a server process.
leader/followers: In this model, the user must
create several threads, all of which invoke
ORB::run
, the ORB will select one of the threads
to wait for incoming requests.
This thread is called the leader thread and will process the
first request that arrives to the ORB, but before
doing so the ORB will selects another thread in the pool to
become the leader.
In other words the threads in the pool take turns to
process the events.
-ORBCollocation
flag as an argument of
ORB_init
(most often thru the command line flags.)
Using the switch -ORBProfileLock this policy can be deactivated specifying -ORBProfileLock null. The primary reason for doing this is to improve performance when no forwarding is used or no multithreading with access to shared CORBA::Object's. Using a null mutex reduces the overhead compared with using a regular mutex lock.
Please see the ORBSVCS
Makefile
for the default setting of
TAO_ORBSVCS
.
Please note that the Naming Service will always be built, even
if Naming is not specified in TAO_ORBSVCS
. That's
because many examples, tests, and presumably applications use it.
Typical Use | This is the default configuration of TAO, where one thread handles requests from multiple clients via a one Reactor. It is appropriate when the requests (1) take a fixed, relatively uniform amount of time and (2) are largely compute bound. |
---|---|
Number of Threads | 1 |
Thread Creator | OS or whoever creates the main ORB thread in a process. |
Thread task | The single thread processes all connection requests and CORBA messages. |
Synchronization considerations | Application servants needn't be concerned with synchronizing their interactions since there's only one thread active with this model. |
Options | The default settings should work just fine (by default,
the -ORBReactorType is tp). However,
you can apply the following options to improve performance: TAO_Advanced_Resource_Factory: -ORBReactorType select_st, -ORBInputCDRAllocator null TAO_Server_Strategy_Factory: -ORBconcurrency reactive (default), -ORBPOALock null TAO_Client_Strategy_Factory: -ORBConnectorLock null |
Check out the Grid for an example of a default configuration and this for an example of settings that would provide better performance.
Typical Use | This configuration spawns a new thread to serve requests from a new connection. This approach works well when there are multiple connections active simultaneously and each request-per-connection may take a fair amount of time to execute. |
---|---|
Number of Threads | 1 thread for the ORB, plus 1 thread for each connection. |
Thread Creator | Programmer must set up the main thread which the ORB lives. The ORB is responsible to create new threads upon new connections. |
Thread task | The main thread handles new connections and spawns new threads for them. Other threads handle requests for established connections. |
Synchronization considerations | To avoid race conditions, application servants may need to synchronize their methods if multiple clients can access them concurrently. |
Options | TAO_Server_Strategy_Factory: -ORBConcurrency thread-per-connection |
IDL_Cubit is a good example on using multiple threads, thread-per-connection configuration.
Typical Use | This model implements a highly optimized, TAO-specific thread pool that minimizes context switching and thread creation costs. In this model, the programmer is responsible of spawning a group of threads, creating an ORB instance, and then instructing all the threads to run the ORB event loop. When a request comes in, one of these waiting threads in the pool will handle the request. |
---|---|
Number of Threads | Thread for the ORB, plus the number of threads used by the thread pool. |
Thread Creator | Pre-spawned by the main thread. |
Thread task | Blocking on the reactor to wait for its turn to handle a request. |
Synchronization considerations | To avoid race conditions, application servants may need to synchronize their methods if multiple clients or multiple thread from the same client can access them concurrently. |
Options | The default ORB settings support this concurrency configuration, though you'll need to spawn the extra threads in the pool explicitly. |
MT_Server is a good example on using multiple threads, single ORB, TAO thread-pool configuration.
Typical Use | This model implements a highly optimized Real-time CORBA thread pool that minimizes context switching, and thread creation costs. In this model, the application is responsible for starting up the ORB and then calling the Real-time CORBA thread pool factory methods that internally spawn a pool of threads. When a request comes in, one of these waiting threads in the pool will handle the request in accordance with the various CORBA policies. |
---|---|
Number of Threads | Thread for the ORB, plus the number of threads used by the thread pool. |
Thread Creator | Static threads are pre-spawned by the ORB, which also spawns any dynamic threads on-demand. |
Thread task | Blocking on the reactor to wait for its turn to handle a request. |
Synchronization considerations | To avoid race conditions, application servants may need to synchronize their methods if multiple clients or multiple thread from the same client can access them concurrently. |
Options | The ORB must be configured to work with Real-time CORBA, at which point the default settings work fine. |
Thread_Pool is a good example on using multiple threads, single ORB, Real-time CORBA thread-pool configuration.
Typical Use | In this configuration, there are multiple ORBs in a process with multiple threads. Each thread handles requests reactively. This model is good for hard real-time applications that require different thread priorities for the various ORBs. |
---|---|
Number of Threads | One thread for each ORB. |
Thread Creator | The main process (thread). |
Thread task | Service the requests from associating ORB. |
Synchronization considerations | Application servants needn't be concerned with synchronizing their interactions if there's no cross ORB/thread access. |
Options | The default settings just works fine. However, one could
use TAO_Advanced_Resource_Factory: -ORBReactorType "which", for a thread-safe platform-specific reactor. |
Typical Use | This approach provides a range of thread priorities plus connections that don't interfere with each others. |
---|---|
Number of Threads | One thread for each ORB, plus one thread for each connection. |
Thread Creator | Main threads creates threads running ORBs. They, in turns, create connection handling threads. |
Thread task | There are threads running ORB's event loops which handle connection requests and handler threads which service requests from established connections. |
Synchronization considerations | To avoid race conditions, application servants may need to synchronize their methods if multiple clients can access them concurrently. |
Options | TAO_Server_Strategy_Factory: -ORBConcurrency thread-per-connection |
MT_Cubit is a good example on using multiple threads, multiple ORBs, and thread-per-connection configuration.
Typical Use | This model incorporates the advantage of using thread-pool while allowing hard real-time system to handle requests in different priority. |
---|---|
Number of Threads | One thread for each ORB, plus the total number of threads in all thread pools |
Thread Creator | Pre-spawned by the main thread. |
Thread task | Handle incoming request for the ORB event loop it is waiting on. |
Synchronization considerations | Application servants needn't be concerned with synchronizing their interactions if there's no cross ORB/thread access. |
Options | The default settings work well for this |
The plain vanilla approach is do nothing. All TAO components use their default settings.
The most common use case is to use a file called
svc.conf
. On most platforms, TAO programs
automatically search and read in the file. The disadvantage of
this approach is you always need a svc.conf
file if
you want to do use non-default configuration.
You can use -ORBSvcConf filename
to use
a config file that is not called svc.conf
.
Specifying -ORBSvcConf
exclude the reading of
default svc.conf
file.
If you don't want the application users to worry about
setting up or knowing about svc.conf
files, you can
call TAO_Internal::default_svc_conf_entries()
before calling the first ORB_init()
in your program
to set up the default svc.conf entries. In this case, if a TAO
application cannot find a svc.conf file, it will configure TAO's
components using the default settings. You can still use a
svc.conf
file or use -ORBSvcConf
option to tune the program.
TAO programs evaluate the configuration settings in the following order:
-ORBSvcConf
command-line
option, if one exist. Otherwise, the
svc.conf
in the start-up directory will be
evaluated, if one exist.
TAO_Internal::default_svc_conf_entries()
, if
ones exist.
Notice that the first encountered component settings are
always the ones take effect. For example, if you set the entries
for Resource_Factory
and
Server_Strategy_Factory
using
TAO_Internal::default_svc_conf_entries()
in a
program and you also have a file called svc.conf
which has an entry for Resource_Factory
. This
program will use the entry for Resource_Factory
in
the svc.conf
file, the entry for
Server_Strategy_Factory
set in the program, and the
in-stock Client_Strategy_Factory
that TAO defines.
Some platforms do not support reading of svc.conf
files or perhaps you would rather not to use this feature. In these cases,
you can define TAO_PLATFORM_SVC_CONF_FILE_NOTSUP
in your ACE config.h
file and recompile the TAO
libraries. When this flag is set, TAO programs will not try to search for
the default svc.conf
file. You can still use
-ORBSvcConf
to initialize the components (assuming
the platform supports it).
On these platform, you can alter the default settings for
TAO components by defining the following macros in your
config.h
file:
TAO_DEFAULT_RESOURCE_FACTORY_ARGS
TAO_ADVANCED_RESOURCE_FACTORY_ARGS
TAO_DEFAULT_SERVER_STRATEGY_FACTORY_ARGS
TAO_DEFAULT_CLIENT_STRATEGY_FACTORY_ARGS
The ACE Makefiles fakesvcconf
flag can be
used to define TAO_PLATFORM_SVC_CONF_FILE_NOTSUP
.
To define that macro, just add fakesvcconf=1
to
your make
invocation.
See orbconf.h
for
an example.
Many real-time applications run on homogenous environments, TAO (and ACE) can take advantage of this fact by simplifying the server side demarshaling; to enable this feature you have to edit the $ACE_ROOT/ace/OS.h file and enable the macro ACE_DISABLE_SWAP_ON_READ.
In this systems it is also common that server and the client startup and shutdown simultaneously, in those circumstances there is no need to check the timestamps in the POA, another macro (POA_NO_TIMESTAMP) can be used for this purpose.
Users running in embebbed systems may also need to modify the default options for TAO, the macros TAO_DEFAULT_RESOURCE_FACTORY_ARGS, TAO_ADVANCED_RESOURCE_FACTORY_ARGS, TAO_DEFAULT_CLIENT_STRATEGY_FACTORY_ARGS and TAO_DEFAULT_SERVER_STRATEGY_FACTORY_ARGS can be used for those purposes. If the footprint size is an issue users may consider writing custom strategy factories that only create the right strategies, this eliminates the parsing code for the different options.
If the only ORB running is TAO and there is no need to be IIOP interoperable the option -ORBGIOPlite can be used to reduce the message size and the processing time.
Unix systems that support local IPC (formerly known as Unix domain sockets) can take advantage of TAO's UIOP pluggable transport protocol to improve performance considerably. To use TAO's UIOP pluggable protocol, simply specify a UIOP endpoint on the command line using the -ORBEndpoint option described in the options documentation. Further performance improvement can be achieved by using the UIOP protocol in combination with the -ORBGIOPlite option. Additional information about TAO's UIOP pluggable protocol can be found in the release notes.
Some embedded systems run without the benefit of a DNS server, in that case they can use the -ORBDottedDecimalAddresses option; the ORB will avoid the use of hostnames in the profiles it generates, thus clients don't need to do any name resolution. Use the compile-time define TAO_USES_DOTTED_DECIMAL_ADDRESSES in $TAO_ROOT/tao/orbconf.h to make this the default behavior.
As the reader will note this is a delicate configuration option, the rule of thumb should be not to use ORB-per-thread unless it is really required.
While waiting for this response new requests to the local ORB can arrive, this is the so-called nested upcall support. TAO supports two mechanisms for handling nested upcalls, the default uses the leader-follower model to allow multiple threads to wait on a single reactor for several concurrent requests; sometimes this configuration can be an overkill, if only one thread is using a reactor at the same time a lighter weight implementation can be used.
This configuration is controlled by the -ORBClientConnectionHandler option, good opportunities to use this option are:
In some cases the user may gain access to the CDR stream buffer: TAO makes no copies when demarshaling octet sequences, instead the octet sequence simply points to the CDR buffer, since the octet sequence does not own this buffer a copy must be made if the user wants to keep the buffer after the upcall.
The user can, however, increase the reference count on the CDR stream buffer, thus allowing her to extend the lifetime of this buffer. Still passing this buffer to another thread and attempting to release it in that thread will result in some memory leak or corruption. Users willing to use this feature of TAO can still do so, if they use a global allocator for their input CDR stream, but that will introduce extra locking on the critical path.
As the reader can see this is an option that has limited applicability and requires careful consideration of the tradeoffs involved.
Back to the TAO component options and tuning documentation.