|Please note that with PowerBuilder 8.0.3 and later you no longer need to set the BindThread property when using DataStores within PowerBuilder EAServer components. This requirement has been elminated due to a change in the implementation of the DataStore to no longer depend on window handles. The discussion below, nevertheless, provides a good overview on the effect of binding components to operating system threads, and it is still very much applicable to PowerBuilder components that are running with versions of the PowerBuilder Virtual Machine (VM) prior to 8.0.3.|
On Microsoft ® Windows ® platforms, the PowerBuilder ® DataStore class is implemented using an underlying operating system construct known as a window handle. The reliance of that implementation upon window handles incorporates the use of a memory resource called Thread Local Storage (TLS). TLS is memory that is associated exclusively with each specific thread and enables the thread to maintain data that are not shared among other threads but that do persist between method calls serviced by that thread. In EAServer, there are special considerations and a resulting scalability impact for components that rely on TLS, such as ActiveX ® components and PowerBuilder components that specifically implement DataStores
In the standard EAServer connection scenario, a thread created by and within the EAServer process is assigned to each client request. That thread is used to execute the business method requested by the client, and after that method has completed, the thread is released to execute another method on a potentially different component instance or to reside in a thread-pool for future use by another client request.
Because TLS is associated specifically with the thread, any data that might have been placed in TLS will continue to be associated with the thread rather than with the component instance itself. As a result, if a subsequent method call on a specific component instance were to be serviced by a different thread and require access to the data stored in TLS by the preceding method, the invocation would fail because the required data would not be stored with the current thread. While TLS is typically not something that PowerBuilder developers directly implement within their PowerScript code, the mere use of the DataStore object brings this scenario into play.
To avoid failures such as described above, EAServer provides a specific property setting for each component called com.sybase.jaguar.component.bind.thread. This property is available on the Instances and All Properties tabs of Jaguar Manager and on the Advanced tab of PowerBuilder's EAServer Component Generator project properties dialog, where it is checked by default. Setting this property for a component directs EAServer to associate each instance of that component with one and only one thread for the lifetime of that instance, thereby enabling the safe usage of TLS.
|Setting the Bind Thread Property|
|Jaguar Manager||PowerBuilder Project Painter|
In regard to PowerBuilder components, it is recommended that you set the bind.thread component property to false when all occurrences of DataStores within the component meet one of the following criteria:
- A DataStore has local variable scope.
- An instance or global DataStore is CREATEd and DESTROYed within the same method in which it is used. (If this is truly the case, then the DataStore variable would be more correctly scoped as a local variable.)
- A DataStore in a stateless component is CREATEd in the activate event and DESTROYed in the corresponding deactivate event.
A stateful component that includes DataStores must be marked with com.sybase.jaguar.component.bind.thread=true, unless all usage of DataStores in that component falls within the first two conditions above. Failure to set the bind.thread property when required can result in silent failures, spurious exceptions, stalled component instances, and general instability.
In the previous paragraphs, stateless corresponds to the component property setting of com.sybase.jaguar.component.tx_vote = false, while stateful indicates that same property has a value of true. On the Transactions tab of Jaguar Manager's Component Properties dialog and on the Components tab of PowerBuilder's EAServer Component Generator project properties dialog this property is labeled Automatic Demarcation / Deactivation.
|Designating a Component as Stateless|
|Jaguar Manager||PowerBuilder Project Painter|
For a truly scalable system, you should strive to use stateless components wherever possible, in which case the BindThread requirement is relatively easy to accommodate for PowerBuilder components. Should a stateful component be unavoidable, keep in mind that additionally requiring threads be bound to component instances further decreases overall system scalability.
Scalability is affected because each thread remains associated with a specific instance until that instance is destroyed. Component instances that are pooled retain their original threads as well, even though those instances are clearly not servicing requests. Each operating system process, EAServer included, can create a maximum of 2028 threads 1; therefore, when there are many pooled instances retaining threads, the number of threads available to respond to new client requests decreases.
1Platform SDK : DLLs, Processes, and Threads : CreateThread, MSDN, http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dllproc/prothred_4084.asp
Sybase and DataWindow are registered trademarks of Sybase, Inc.