Midnight Home   *   Support Home   *   K Home  
Vantive Cases   Technotes   All   Defects   Old Cases   --   Case Report   --   Q   --   Help

[Previous Doc] [Next Doc]

TechnoteID: 12981   Vantive creation date: 8/24/00   Modified: 8/31/00
State Type Product Group Product Impact Created by Modified by
Publish External Rose RealTime Rose-RT Low tmcguire / Thomas McGuire sbenetea / Stephen Beneteau

Subject: Dynamic Thread Creation in Rose RealTime

PRODUCT: Rose RealTime 6.x / 200x

OS: Windows NT/2000, Sun Solaris 2.5, 2.6, 2.7, HP-UX 10.20

DEFECT #: N/A

PATCH #: N/A

REFERENCES: N/A

CREATED: 2000.08.24
REVISED: N/A

QUESTION:   How can you create threads dynamically in Rose RealTime?

ANSWER:   Dynamic Thread creation in Rose RealTime models is easily accomplished
using two platform-independent API calls*, one which creates a thread
controller, and another which creates the actual physical thread.  


I.   Creating a Thread Controller

All threads in a Rose RealTime model that will host Capsule references must run
an instance of either RTPeerController or RTCustomController.   RTPeerController
is the default thread controller used for most applications.   Users who need
more control over the thread may wish to use RTCustomController.   More
information about RTCustomController is available in the online help.

The constructors for RTCustomController and RTPeerController are defined as:

      RTCustomController::RTCustomController( RTDebugger * debug,
      const char * rtsname )

      RTPeerController::RTPeerController( RTDebugger * debug,  
      const char * rtsname )


As you can see, each constructor requires a pointer to an RTDebugging object,
present in models with Target Observability enabled.   The debugger is available
through a call to 'context()->debugger()'   In applications where Target
Observability has been compiled-out of the Target RTS, dynamic thread creation
will not be effected.   The second parameter is the symbolic name for the thread
on which the controller will run.   This name can be any string the developer
deems applicable, and will not be used in subsequent calls to the RTS.

A complete constructor call will look like:

                    RTPeerController * dynController;
      char * threadName = "myPhysicalThread"
      dynController = new RTPeerController( context()->debugger(), threadName );
//could have called RTCustomController

From this point on, dynController represents a valid RTPeerController object.

II Creating a Physical Thread

After a thread controller is instantiated, it can be used as a starting point
at which to create a physical thread.   Physical thread creation is accomplished
by a platform-independent RTThread object.   The constructor for this class is
defined as:

      RTThread::RTThread( RTJob * job, int stack_size, int prio )

Since both RTPeerController and RTCustomController classes are derived from the
RTJob class, we pass the RTPeerController * dynController (created above) as
the first parameter.   The stack size is user-defined, but the default value for
Rose RealTime models is 20000.   The third attribute is the thread priority.  
Constants have been defined in $(ROSERT_HOME)\C++\TargetRTS\target\<targetname>\
RTTarget.h which are recommended for use here.   The default priority for
threads in Rose RealTime models is defined in DEFAULT_MAIN_PRIORITY.  

A complete call to the thread contstructor will look like:

      RTThread * dynThread;
      dynThread = new RTThread( dynController, 20000, DEFAULT_MAIN_PRIORITY );
//dynController defined above

III Using The New Physical Threads

Once a thread and its controller is instantiated, capsules can be instantiated
to run on the thread via calls to the Frame service.   An example of a call to
the Frame service is:

      RTActorIde( RTActorRef & capsule_role, const RTTypedValue & info, RTController
* log_thread = 0, int index = -1 )

The first two parameters indicate the capsule role to be incarnated, and any
information to be passed to the newly-instantiated capsule reference.   The
third parameter is the RTPeerController created in step I.   The final parameter
indicated the index and is used in case of a replicated capsule reference.   A
complete Frame service call is:

      frame.incarnate( worker, (void *)0, dynController, -1 ) //where frame is the
name of a Frame port in the containing capsule reference
      //where 'worker' is the name of the capsule reference

IIII Destroying the physical threads

Before destroying a physical thread, it is recommended that all capsule
references incarnated on the thread be explicitly destroyed by a call to
Frame::destroy.

Threads and their controllers should be destroyed opposite to their creation
order.   That is, since the controller was created first, it should be destroyed
last.   Destruction of the controller and thread is as simple as using the
delete command to invoke the class destructor functions.   To destroy the thread
and controller created above use:

      if (frame.destroy(worker)) // returns non-zero to indicate successful
destruction
      {
      delete dynThread;
      delete dynController;
      }


IV Example Model

A model demonstrating this technique is available on the support website or
through technical support.

*Please note that dynamic thread creation uses some calls that are internal to
the TargetRTS. Some of the calls are not part of the public API and
hence, may change without prior notice. Also, if changed, a migration path
might not necessarily be provided by Rational. Use of this example is at the
discretion of the customer and is not officially supported.

For more information contact Rational Customer Support

This report was generated on Sun Dec 3 17:14:27 2000 (Local server time).

[Previous Doc] [Next Doc]
Vantive Cases   Technotes   All   Defects   Old Cases   --   Case Report   --   Q   --   Help

Copyright © 1995-2000 Rational Software Corporation.  All rights reserved.
Legal information and policies | Privacy Statement