home *** CD-ROM | disk | FTP | other *** search
/ Programming Languages Suite / ProgramD2.iso / Visual Database / Visual BASIC 5.0 (Ent. Edition) / Vb5ent Extractor.EXE / VB / SAMPLES / ENTRPRIS / APE / AECLIENT / MODCLNT.BAS < prev   
Encoding:
BASIC Source File  |  1996-12-23  |  42.2 KB  |  936 lines

  1. Attribute VB_Name = "modClient"
  2. Option Explicit
  3. '-------------------------------------------------------------------------
  4. 'The project is the Client component of the Application Performance Explorer
  5. 'This client is designed to be instanciated by and configured by the APE
  6. 'Manager.  It can generate Service Request by calling the QueueManager.
  7. 'Or it can call the Worker to produce synchronous work.  In either of these
  8. 'sinarios the frequency can vary, and the type and size of data it passes
  9. 'can vary.
  10. '
  11. 'Key Files:
  12. '   frmClnt.frm     The only form in the app
  13. '   Client.cls      Single-use, creatable, public class that provides
  14. '                   OLE interface for Manager to instanciate and configure
  15. '   clsCalbk.cls    Not creatable, but public class that is passed to the
  16. '                   QueueMgr to receive call backs
  17. '   clsCntSv.cls    Class used to store data on expected callbacks
  18. '   clsDrtTl.cls    Class providing a runtest method for running direct
  19. '                   instanciation tests
  20. '   clsPosFm.cls    Tool form saving form position to registry
  21. '   clsQueTl.cls    Class providing a runtest method for running Queue
  22. '                   manager tests
  23. '-------------------------------------------------------------------------
  24.  
  25. 'Declares
  26. #If UNICODE Then
  27.     Declare Function GetTempFileName Lib "kernel32" Alias "GetTempFileNameW" (ByVal lpszPath As String, ByVal lpPrefixString As String, ByVal wUnique As Long, ByVal lpTempFileName As String) As Long
  28.     Declare Function GetTempPath Lib "kernel32" Alias "GetTempPathW" (ByVal nBufferLength As Long, ByVal lpBuffer As String) As Long
  29.     Public Declare Function GetComputerName Lib "kernel32" Alias "GetComputerNameW" (ByVal lpBuffer As String, nSize As Long) As Long
  30. #Else
  31.     Declare Function GetTempFileName Lib "kernel32" Alias "GetTempFileNameA" (ByVal lpszPath As String, ByVal lpPrefixString As String, ByVal wUnique As Long, ByVal lpTempFileName As String) As Long
  32.     Declare Function GetTempPath Lib "kernel32" Alias "GetTempPathA" (ByVal nBufferLength As Long, ByVal lpBuffer As String) As Long
  33.     Public Declare Function GetComputerName Lib "kernel32" Alias "GetComputerNameA" (ByVal lpBuffer As String, nSize As Long) As Long
  34. #End If
  35. Public Declare Function GetTickCount Lib "kernel32" () As Long
  36.  
  37. 'Caption String Constants
  38. Public Const giFORM_CAPTION  As Integer = 101                   'Form Caption
  39. Public Const giCALLS_MADE_CAPTION  As Integer = 102
  40. Public Const giCALLS_RETURNED_CAPTION  As Integer = 103
  41.  
  42. 'Log String Constants
  43. Public Const giCOMPONENT_NAME  As Integer = 2
  44. Public Const giCALLBACK_RECEIVED  As Integer = 3
  45. Public Const giCALLBACK_ERROR_RECEIVED  As Integer = 4
  46. Public Const giQUEUE_SERVICE  As Integer = 5
  47. Public Const giQUEUE_SERVICE_ERROR  As Integer = 7
  48. Public Const giQUEUE_SERVICE_COLLISION_RETRY  As Integer = 9
  49. Public Const giWAIT_PERIOD_ERROR  As Integer = 12
  50. Public Const giSTART_TEST  As Integer = 13
  51. Public Const giSTOP_TEST  As Integer = 14
  52. Public Const giTEST_STARTED  As Integer = 16
  53. Public Const giTEST_COMPLETE  As Integer = 17
  54. Public Const giSERVICES_POSTED  As Integer = 18
  55. Public Const giCALLBACKS_COMPLETE As Integer = 19
  56. Public Const giDIRECT_SERVICE  As Integer = 21
  57. Public Const giWRITING_TEMP_FILE  As Integer = 23
  58. Public Const giUSING_NO_AUTHENTICATION  As Integer = 24
  59. Public Const giDISK_FULL As Integer = 26
  60. Public Const giPOOL_MGR_REJECTION_WAITS_EXHAUSTED As Integer = 27
  61.  
  62. Public Const giFONT_CHARSET_INDEX As Integer = 30
  63. Public Const giFONT_NAME_INDEX As Integer = 31
  64. Public Const giFONT_SIZE_INDEX  As Integer = 32
  65.  
  66. Public Const giERROR_PREFIX  As Integer = 50                ' "Error:  "
  67.  
  68. Public Const giRACREG_ERROR_CODE_OFFSET As Integer = 200               'Add offset to racreg32 error codes
  69.                                                             'to make corresponding resource string key
  70. 'Application Error Constants
  71. Public Const giCOLLISION_ERROR  As Integer = 32767          'OLE collision retries exausted
  72. Public Const giREQUIRED_PARAMETER_IS_MISSING As Integer = 32765
  73. Public Const giPOOLMGR_RETURNED_NOTHING As Integer = 32766
  74. Public Const giCONNECTION_SETTING_FAILED As Integer = 32750     'An error was returned by RacReg32
  75. 'Queue Manager errors
  76. Public Const giQUEUE_MGR_IS_BUSY As Integer = 32749
  77.  
  78. 'Other Constants
  79. Public Const giCALL_SENT_AND_RECEIVED_MAX_DIFFERENCE As Integer = 200   'If the number of calls that the
  80.                                                                 'client has made is this much greater than
  81.                                                                 'the number of calls received back then
  82.                                                                 'pause making calls until callbacks catch up
  83. Public Const giREDIM_CHUNK_SIZE  As Integer = 100               'Size of redimension chunks of log array
  84. Public Const giNO_RECORD  As Integer = -1                       'Flag value meaning no records
  85. Public Const giMAX_ALLOWED_RETRIES  As Integer = 500            'Max allowed OLE automation call retries
  86. Public Const giRETRY_WAIT_MIN  As Integer = 1000                'Retry Wait is measure in DoEvent cyles
  87. Public Const giRETRY_WAIT_MAX  As Integer = 5000
  88. Public Const giROWS_RETURNED_PER_GET_RECORDS As Integer = 500   'Max number of records returned for
  89.                                                                 'each call of GetRecords
  90. Public Const RPC_C_AUTHN_LEVEL_NONE  As Integer = 1             'Remote Automation Authentication level constant
  91. Public Const giPOOL_WAIT_RETRY_MIN As Integer = 1000            'The minum milliseconds to wait if the Pool Manager
  92.                                                                 'rejects request for a Worker
  93. Public Const giQUEUE_WAIT_RETRY_MIN As Integer = 3000           'The minimum to wait in milliseconds if the Queue
  94.                                                                 'raises an error that it is to busy to process
  95.                                                                 'a Service Request
  96. Public Const glMAX_LONG As Long = 2147483647
  97. Public Const giDEFAULT_TIMER_INTERVAL As Integer = 100
  98.  
  99. 'Type
  100. Public Type RANDOM_DATA_GROUP
  101.     Random As Boolean
  102.     SpecificValue As Long
  103.     UpperValue As Long
  104.     LowerValue As Long
  105. End Type
  106.  
  107. 'Global Variables and Objects
  108. Public goTestTool As Object             'Object of a class having RunTest method
  109.                                         'actually runs the test.  Different classes
  110.                                         'are used for different types of tests
  111. Public gcServices As Collection         'Collection of clsCllietnService class objects
  112.                                         'stores expected callback information
  113. Public gaLog() As Variant               'Array that stores log records
  114. Public glCallsMade As Long              'Number of calls made in test
  115. Public glCallsReturned As Long          'Number of callbacks made in a test
  116. Public glInstances As Long              'Count of intances of Client class
  117. Public glLogThresholdRecs As Long       'Log threshold in record count
  118. Public goRegClass As RacReg.RegClass    'RacReg used to change connection settings
  119. Public glLastAddedRecord As Long        'Last added log record array index
  120. Public glFirstServiceTick As Long       'Milliseconds of test start
  121. Public glLastCallbackTick As Long       'Milliseconds of end of test
  122. Public gsTempFile As String             'Temporary log file name
  123.  
  124. 'Flags
  125. Public gbTestInProcess As Boolean           'If true, test is in process
  126. Public gbStopping As Boolean                'If true, stopping test, procedures check it
  127. Public gbShutDown As Boolean                'If true, shutting down client
  128. Public gbRunCompleteProcedure As Boolean    'Timer will run CompleteTest
  129. Public gbRunning As Boolean                 'In a RunTest method
  130. Public gbGetWrittenLogCalled As Boolean     'GetWritten log was called
  131.  
  132. 'Public Property Variables
  133. Public gsServiceCommand As String               'Command string to pass to Queue.Add
  134. Public gbUseDefaultService As Boolean           'If true use default service object
  135. Public gudtWaitPeriod As RANDOM_DATA_GROUP      'How long to wait between calls
  136. Public glNumberOfCalls As Long                  'Number of Calls to make in test
  137. Public glTestDurationInTicks As Long            'Number of Milliseconds for Test to last
  138. Public giTestDurationMode As Integer            'Mode of determining test duration
  139. Public gudtSendNumRows As RANDOM_DATA_GROUP     'Number of rows of data to send with Service request
  140. Public gudtSendRowSize As RANDOM_DATA_GROUP     'Number of bytes of data to put in each row of data
  141. Public glSendContainerType As Long              'Type of data to send with Service request
  142. Public gudtReceiveNumRows As RANDOM_DATA_GROUP  'Number of rows to request back from Service request
  143. Public gudtReceiveRowSize As RANDOM_DATA_GROUP  'Size of each row in bytes to request back
  144. Public glReceiveContainerType As Long           'Container type to request back from Service request
  145. Public gudtTaskDuration As RANDOM_DATA_GROUP    'Length of time a Service request should take
  146. Public glServiceTask As Integer                'Code for whether Service should use processor cycles during
  147. Public giUseProcPercent As Integer              'Percentage of requests that services should use processor
  148.  
  149. Public gbShow As Boolean                'If true, show frmClient during test
  150. Public gbLog As Boolean                 'If true log events during test
  151. Public glCallbackMode As Long           'Determines if and how client receives results from
  152.                                         'services requested from QueueManager
  153.                                         'see "Callback mode keys" in modAEConstants
  154. Public gbLogWorker As Boolean           'If true, have directly instanciated worker log
  155. Public gbPreloadServices As Boolean     'If true, have directly instanciated worker preload
  156.                                         'needed service object
  157. Public gbPersistentServices As Boolean  'If true, have directly instanciated worker retain
  158.                                         'references to Service objects
  159. Public gbEarlyBindServices As Boolean   'If true, have directly instanciated workers use
  160.                                         'earlybound service objects
  161. Public glModel As Long                  'APE framework model to use during test
  162. Public glClientID As Long               'Client ID Manager uses to manager Client object
  163. Public gsConnectionAddress As String    'Net address of APE server objects to use
  164. Public gsConnectionProtocol As String   'Protocol to connect with
  165. Public glConnectionAuthentication As String 'Authentiation level to use
  166. Public gbConnectionRemote As Boolean    'If true, connect to a remote server not local
  167. Public gbConnectionNetOLE As Boolean    'If true, use NetOLE (DCOM) instead of Remote Automation
  168. Public goExplorer As APEInterfaces.Manager 'Explorer object passed to client from Manager
  169.                                            'Client calls manager back with this
  170. Public glLogThreshold As Long           'Log threshodl in kilobytes
  171.  
  172.  
  173. Sub Main()
  174. End Sub
  175.  
  176. Public Sub CompleteTest()
  177.     '-------------------------------------------------------------------------
  178.     'Purpose:   Release objects used during test, and call Manager with
  179.     '           notification the test.
  180.     'Effects:
  181.     '   [gbTestInProcess]
  182.     '           becomes false
  183.     '   [goTesttool]    destroyed
  184.     '   [goExplorer]    destroyed
  185.     '   [gcServices]    destroyed
  186.     '-------------------------------------------------------------------------
  187.     Dim s As String
  188.     Static stbInCompleteTest As Boolean 'If true already in this procedure
  189.     
  190.     'Exit if reentry caused by timer click
  191.     'while calling goExplorer
  192.     
  193.     If stbInCompleteTest Then Exit Sub
  194.     stbInCompleteTest = True
  195.     On Error GoTo CompleteTestError
  196.     s = LoadResString(giTEST_COMPLETE)
  197.     If gbLog Then AddLogRecord 0, s, GetTickCount(), False
  198.     DisplayStatus s
  199.     If Not goExplorer Is Nothing Then goExplorer.Done
  200.     Set goTestTool = Nothing
  201.     Set gcServices = Nothing
  202.     stbInCompleteTest = False
  203.     gbTestInProcess = False
  204.     Exit Sub
  205. CompleteTestError:
  206.     Select Case Err.Number
  207.         Case RPC_E_CALL_REJECTED
  208.             'Collision error, the OLE server is busy
  209.             Dim iRetry As Integer
  210.             Dim il As Integer
  211.             Dim ir As Integer
  212.             If gbLog Then AddLogRecord 0, LoadResString(giQUEUE_SERVICE_COLLISION_RETRY), GetTickCount(), False
  213.             If iRetry < giMAX_ALLOWED_RETRIES Then
  214.                 iRetry = iRetry + 1
  215.                 ir = Int((giRETRY_WAIT_MAX - giRETRY_WAIT_MIN + 1) * Rnd + giRETRY_WAIT_MIN)
  216.                 For il = 0 To ir
  217.                     DoEvents
  218.                 Next il
  219.                 Resume
  220.             Else
  221.                 'We reached our max retries
  222.                 If gbLog Then AddLogRecord 0, LoadResString(giCOLLISION_ERROR), GetTickCount(), False
  223.                 Resume Next
  224.             End If
  225.         Case Else
  226.             s = LoadResString(giQUEUE_SERVICE_ERROR) & CStr(Err.Number) & gsSEPERATOR & Err.Source & gsSEPERATOR & Err.Description
  227.             If gbLog Then AddLogRecord 0, s, GetTickCount(), False
  228.             stbInCompleteTest = False
  229.             Err.Raise Err.Number, Err.Source, Err.Description
  230.             Exit Sub
  231.     End Select
  232. End Sub
  233.  
  234.  
  235. Public Sub gStopTest()
  236.     '-------------------------------------------------------------------------
  237.     'Purpose:   To stop cancel the current test
  238.     'Assumes:   If gbRunning is true, a method procedure or a callback method
  239.     '           are being processed.  We can exit this procedure and one of those
  240.     '           methods will check the gbStopping flag and call gStopTest again
  241.     '           If gbShutDown is true, then this procedure was called by the
  242.     '           Terminate event of the Client class on the release of its last
  243.     '           reference
  244.     'Effects:
  245.     '   [gbTestInProcess]
  246.     '                   becomes false
  247.     '   [goTesttool]    destroyed
  248.     '   [goExplorer]    destroyed
  249.     '   [gcServices]    destroyed
  250.     '   [goRegClass]
  251.     '           If gbShutDown is true destroy goRegClass
  252.     '   [frmClient]
  253.     '           If gbShutDown is true unload
  254.     '-------------------------------------------------------------------------
  255.     Dim oCA As clsClientService
  256.     Dim s As String
  257.     On Error GoTo gStopTestError
  258.     
  259.     gbStopping = True
  260.     s = LoadResString(giSTOP_TEST)
  261.     If gbLog Then AddLogRecord 0, s, GetTickCount(), False
  262.     DisplayStatus s
  263.     'Make sure we are not in the middle of queueing an Service.
  264.     'If we are, get out.  QueueService will check the gbStopping flag
  265.     'and call the gStopTest method again when it's done.
  266.     glLastCallbackTick = GetTickCount()
  267.     If gbRunning Then Exit Sub
  268.     Set goTestTool = Nothing
  269.     Set gcServices = Nothing
  270.     gbTestInProcess = False
  271.     'See if this was called by Terminate if it was unload form
  272.     If gbShutDown Then
  273.         Set goRegClass = Nothing
  274.         Unload frmClient
  275.     End If
  276.     Exit Sub
  277. gStopTestError:
  278.     Select Case Err.Number
  279.         Case Else
  280.             LogError Err
  281.             If glInstances > 0 Then Err.Raise Err.Number, Err.Source, Err.Description
  282.             Resume Next
  283.     End Select
  284. End Sub
  285.  
  286.  
  287. Public Sub AddServiceRecord(lID As Long, sCommand As String, lTicks As Long)
  288.     '-------------------------------------------------------------------------
  289.     'Purpose:   Put a new Service Request in the Service collection.
  290.     'In:
  291.     '   [lID]   Service Request ID
  292.     '   [sCommand]
  293.     '           Service Request Command sent to QueueMgr
  294.     '   [lTicks]
  295.     '           Tick count at time of call to QueueMgr
  296.     'Effects:
  297.     '   [gcServices]
  298.     '           Adds a clsClientService class object to collection
  299.     '-------------------------------------------------------------------------
  300.     Dim oCA As clsClientService     'Object with properties designed to store
  301.                                     'Service request information
  302.     
  303.     Set oCA = New clsClientService
  304.     With oCA
  305.         .lID = lID
  306.         .sCommand = sCommand
  307.         .lStartTicks = lTicks
  308.     End With
  309.     gcServices.Add oCA, CStr(oCA.lID)
  310. End Sub
  311.  
  312. Public Sub WriteLog()
  313.     '-------------------------------------------------------------------------
  314.     'Purpose:   Writes the current log records to a temp file and
  315.     '           removes the records from memory
  316.     'Assumes:   If gbGetWrittenLogCalled is true, any records currently in the
  317.     '           temporary file are no longer needed, but the file may still be
  318.     '           open.
  319.     'Effects:
  320.     '           All records currently in gaLog are written to a temporary file
  321.     '           and removed from the array
  322.     '   [gbGetWrittenLogCalled]
  323.     '           becomes false
  324.     '   [glLastAddedRecord]
  325.     '           becomes giNO_RECORD
  326.     '   [gaLog] becomes redimension to store new records
  327.     '-------------------------------------------------------------------------
  328.     'Don't save the Component name because the component
  329.     'is always the same
  330.     Dim lServiceID As Long
  331.     Dim sComment As String
  332.     Dim lMilliseconds As Long
  333.     Dim lFile As Long
  334.     Dim l As Long
  335.     On Error GoTo WriteLogError
  336.     If glLastAddedRecord > giNO_RECORD Then
  337.         AddLogRecord 0, LoadResString(giWRITING_TEMP_FILE), GetTickCount, False
  338.         
  339.         'Check to see if the contents of the temp file
  340.         'need deleted first, the reason it is not delete
  341.         'when the flag is flipped is to give one the chance
  342.         'of rescueing it if the Manager fails to retreive
  343.         'the records from it
  344.         If gbGetWrittenLogCalled Then
  345.             Close   'Close in case last GetWrittenLogs cancelled
  346.             Kill gsTempFile
  347.             gbGetWrittenLogCalled = False
  348.         End If
  349.             
  350.         lFile = FreeFile
  351.         Open gsTempFile For Append As lFile
  352.             For l = 0 To glLastAddedRecord
  353.                 lServiceID = gaLog(giSERVICE_ELEMENT, l)
  354.                 sComment = gaLog(giCOMMENT_ELEMENT, l)
  355.                 lMilliseconds = gaLog(giMILLI_SECONDS_ELEMENT, l)
  356.                 Write #lFile, lServiceID, sComment, lMilliseconds
  357.                 'Reset logrecord counter no after writing the first record
  358.                 'so that records are not added after the count that is being
  359.                 'written and therefore, lost.  This also protects from
  360.                 'Addlogrecord trying to write a record greater than
  361.                 'giREDIM_CHUNK_SIZE write after gaLog is redimensioned
  362.                 If l = 0 Then glLastAddedRecord = giNO_RECORD
  363.             Next
  364.         Close #lFile
  365.         'Remove LogRecords from memory
  366.         'Preserve is used because there is a potential
  367.         'for a log record to be added after the above line
  368.         'but before the following one
  369.         ReDim Preserve gaLog(giLOG_ARRAY_DIMENSION_ONE, giREDIM_CHUNK_SIZE)
  370.     End If
  371.     Exit Sub
  372. WriteLogError:
  373.     Select Case Err.Number
  374.         Case ERR_DISK_FULL
  375.             'Turn off logging erase array
  376.             'leave present file for later retrieval
  377.             DisplayStatus LoadResString(giDISK_FULL)
  378.             Close lFile
  379.             Erase gaLog
  380.             gbLog = False
  381.             Exit Sub
  382.         Case ERR_FILE_NOT_FOUND
  383.             'There is no temp file to kill
  384.             Resume Next
  385.         Case Else
  386.             Close lFile
  387.             Err.Raise Err.Number, Err.Source, Err.Description
  388.             Exit Sub
  389.     End Select
  390. End Sub
  391.  
  392.  
  393. Public Sub GetWrittenLog()
  394.     '-------------------------------------------------------------------------
  395.     'Purpose:   Checks to see if there is log records written to a temp file
  396.     '           If there are it inputs it and adds it to the gaLog array
  397.     '           If it reaches the chunk size for passing log records it will
  398.     '           exit the loop, leaving the file open. It is necessary to keep
  399.     '           calling this function until no records or added.  Do not call
  400.     '           this function more than once until the array that was filled
  401.     '           was erased.  The external process that is calling a method that
  402.     '           calls this procedure should be responsible for calling until
  403.     '           all records have been attained.
  404.     'Effects:
  405.     '           [gbGetWrittenLogCalled] becomes true
  406.     '           Temp file may be left open if all records are not read
  407.     '           AddlogRecord is called for each record read
  408.     'Assumption:
  409.     '           If gbGetWrittenLogCalled is true then the temp file is already
  410.     '           open, ready for the next record to be read.
  411.     '           If the EOF is not reached before the glROWS_RETURNED_PER_GET_RECORDS
  412.     '           is reached then the external process that called Logger.GetRecords
  413.     '           will call it again, to get the rest of the records
  414.     '-------------------------------------------------------------------------
  415.     
  416.     Static stlFile As Long      'File number
  417.     Dim sPath As String         'Path and file name of temporary file
  418.     Dim lServiceID As Long      'Service Request ID
  419.     Dim sComment As String      'Comment in log record
  420.     Dim lMilliseconds As Long   'Milliseconds in log record
  421.     Dim lAddedCount As Long     'Count of how many records have been read and added to memory
  422.     
  423.     On Error GoTo GetWrittenLogError
  424.     sPath = gsTempFile
  425.     
  426.     'Open file if it is not open yet
  427.     If Not gbGetWrittenLogCalled Then
  428.         'Write records in memory first to order the records
  429.         'with any records that may have already been written
  430.         WriteLog
  431.         gbGetWrittenLogCalled = True
  432.         stlFile = FreeFile
  433.         Open sPath For Input As stlFile
  434.     End If
  435.     
  436.     Do Until EOF(stlFile)
  437.         'Component was not saved to temp file because
  438.         'the component name is always the same in this file
  439.         Input #stlFile, lServiceID, sComment, lMilliseconds
  440.         AddLogRecord lServiceID, sComment, lMilliseconds, True
  441.         lAddedCount = lAddedCount + 1
  442.         'Exit here if max record size was reached
  443.         If lAddedCount = giROWS_RETURNED_PER_GET_RECORDS Then Exit Sub
  444.     Loop
  445.     Close
  446.     Exit Sub
  447. GetWrittenLogError:
  448.     Select Case Err.Number
  449.         Case ERR_FILE_NOT_FOUND
  450.             'There are no written records so exit
  451.             Exit Sub
  452.         Case ERR_BAD_FILE_NAME
  453.             'We have already reached the end of the file
  454.             'and it has been closed
  455.             Exit Sub
  456.         Case Else
  457.             Close
  458.             Err.Raise Err.Number, Err.Source, Err.Description
  459.             Exit Sub
  460.     End Select
  461. End Sub
  462.  
  463.  
  464. Public Function GetTempFile() As String
  465.     '-------------------------------------------------------------------------
  466.     'Purpose:   Gets a temp file name from the system
  467.     'Return:    a valid temporary file name
  468.     '-------------------------------------------------------------------------
  469.     Dim lSize As Long
  470.     Dim sPath As String
  471.     Dim sName As String
  472.     Dim lResult As Long
  473.     
  474.     sPath = Space(255)
  475.     lResult = GetTempPath(255, sPath)
  476.     sPath = Left$(sPath, lResult)
  477.     sName = Space(255)
  478.     lResult = GetTempFileName(sPath, "AEC", 0, sName)
  479.     lResult = InStr(sName, vbNullChar)
  480.     sName = Left$(sName, lResult - 1)
  481.     
  482.     GetTempFile = sName
  483. End Function
  484.  
  485. Public Sub DisplayString(s As String)
  486.     '-------------------------------------------------------------------------
  487.     'Purpose:   Adds the passed text to to the list box.  Only used if conditional
  488.     '           compile ccShowList is true.
  489.     'Assumes:   If gbShow is true, form is visible
  490.     '           If ccShowList is true, lstLog is visible and positioned
  491.     '-------------------------------------------------------------------------
  492.     If gbShow Then
  493.         With frmClient.lstLog
  494.             If .ListCount = giLIST_BOX_MAX Then .Clear
  495.             .AddItem s, 0
  496.         End With
  497.     End If
  498. End Sub
  499.  
  500. Public Sub DisplayStatus(s As String)
  501.     '-------------------------------------------------------------------------
  502.     'Purpose:   If gbShow is true, displays passed string on forms status box
  503.     'Assumes:   If gbShow is true, form is loaded and visible
  504.     '-------------------------------------------------------------------------
  505.     If gbShow Then
  506.         With frmClient.lblStatus
  507.             .Caption = s
  508.             .Refresh
  509.         End With
  510.     End If
  511. End Sub
  512.  
  513.  
  514. 'Puts a new log record into the private log array and updates the listbox
  515. 'if the the UI is visible.  The logs will besent to the manager later.
  516. Public Sub AddLogRecord(lServiceID As Long, sComment As String, lMilliseconds As Long, bIgnoreThreshod As Boolean)
  517.     '-------------------------------------------------------------------------
  518.     'Purpose:   Called to add a record to the gaLog.
  519.     'In:        [lServiceID]    Service ID that will be added
  520.     '           [sComment]      Comment that will be added
  521.     '           [lMilliseconds] Milliseconds that will be added
  522.     '           [bIgnoreThreshold]
  523.     '                           If true, procedure ignores the Threshold property
  524.     '                           It will not write the records to a file and
  525.     '                           remove them from the array
  526.     'Effects:   [gaLog]         May be redimensioned (preserve) to increase
  527.     '                           its size
  528.     '           [glLastAddedRecord]
  529.     '                           will be increased by one
  530.     '-------------------------------------------------------------------------
  531.     Dim lU As Long      'Ubound of array
  532.     Dim lIndex As Long  'array index to put records in
  533.  
  534.     On Error GoTo AddLogRecordError
  535. AddLogRecordTop:
  536.     If gbLog Then
  537.         
  538.         'Check if the array needs dimensioned
  539.         If glLastAddedRecord = giNO_RECORD Then
  540.             ReDim gaLog(giLOG_ARRAY_DIMENSION_ONE, giREDIM_CHUNK_SIZE)
  541.             glLastAddedRecord = 0
  542.             lIndex = glLastAddedRecord
  543.         Else
  544.             lU = UBound(gaLog, 2)
  545.             glLastAddedRecord = glLastAddedRecord + 1
  546.             lIndex = glLastAddedRecord
  547.             If glLastAddedRecord > lU Then
  548.                 'Redim gaRecords to increase size
  549.                 lU = lU + giREDIM_CHUNK_SIZE
  550.                 ReDim Preserve gaLog(giLOG_ARRAY_DIMENSION_ONE, lU)
  551.             End If
  552.         End If
  553.         gaLog(giCOMPONENT_ELEMENT, lIndex) = LoadResString(giCOMPONENT_NAME) & Str$(glClientID)
  554.         gaLog(giSERVICE_ELEMENT, lIndex) = lServiceID
  555.         gaLog(giCOMMENT_ELEMENT, lIndex) = sComment
  556.         gaLog(giMILLI_SECONDS_ELEMENT, lIndex) = lMilliseconds
  557.         If Not bIgnoreThreshod And glLogThresholdRecs > 0 And glLogThresholdRecs = glLastAddedRecord Then
  558.            'Write the log file
  559.            WriteLog
  560.         End If
  561.     End If
  562.     #If ccShowList Then
  563.         DisplayString CStr(lServiceID) & gsSEPERATOR & sComment: DoEvents
  564.     #End If
  565.     Exit Sub
  566. AddLogRecordError:
  567.     Select Case Err.Number
  568.         Case ERR_SUBSCRIPT_OUT_OF_RANGE
  569.             'Synchronicity issues caused this
  570.             'Got the glLastAddedRecord write before it got changed
  571.             'but tried to put record in array right after it got redim'ed
  572.             Dim bTried
  573.             'If already tried raise error
  574.             If bTried Then Err.Raise Err.Number, Err.Source, Err.Description
  575.             bTried = True
  576.             'Try the at the top again, getting a new glLastAddedRecord
  577.             GoTo AddLogRecordTop
  578.         Case Else
  579.             DisplayStatus Err.Description
  580.             Exit Sub
  581.     End Select
  582. End Sub
  583.  
  584. Public Sub LogError(ByVal oErr As ErrObject)
  585.     '-------------------------------------------------------------------------
  586.     'Purpose:   Display error description on forms Status box if the form is
  587.     '           visible; log error if logging is on
  588.     'In:        [oErr]
  589.     '               Valid error object
  590.     '-------------------------------------------------------------------------
  591.     Dim s As String
  592.     s = LoadResString(giERROR_PREFIX) & Str$(oErr.Number) & gsSEPERATOR & oErr.Source & gsSEPERATOR & oErr.Description
  593.     If gbLog Then AddLogRecord 0, s, GetTickCount(), False
  594.     DisplayStatus oErr.Description
  595. End Sub
  596.  
  597. Function GetValueFromRange(udtRangeData As RANDOM_DATA_GROUP, bRandomValueRequired As Boolean) As Long
  598.     Dim lReturn As Long
  599.     
  600.     With udtRangeData
  601.         If .Random Then
  602.             Randomize
  603.             lReturn = CLng((.UpperValue - .LowerValue + 1) * Rnd + .LowerValue)
  604.         Else
  605.             lReturn = .SpecificValue
  606.         End If
  607.         If Not bRandomValueRequired Then bRandomValueRequired = .Random
  608.     End With
  609.     GetValueFromRange = lReturn
  610. End Function
  611.  
  612. Function GetServiceCommand(bRandomCommandRequired As Boolean) As String
  613.     Dim sSendCommand As String
  614.     Dim iRandom As Integer
  615.     
  616.     bRandomCommandRequired = False
  617.     'Get ServiceCommand to use
  618.     If gbUseDefaultService Then
  619.         Select Case glServiceTask
  620.             Case giUSE_PROCESSOR_NEVER
  621.                 sSendCommand = gsSERVICE_LIB_CLASS & "." & gsSERVICE_DONT_USE_PROCESSOR
  622.             Case giUSE_PROCESSOR_ALWAYS
  623.                 sSendCommand = gsSERVICE_LIB_CLASS & "." & gsSERVICE_USE_PROCESSOR
  624.             Case giREAD_DATABASE
  625.                 sSendCommand = gsSERVICE_LIB_CLASS & "." & gsSERVICE_READ_DATA
  626.             Case giWRITE_DATABASE
  627.                 sSendCommand = gsSERVICE_LIB_CLASS & "." & gsSERVICE_WRITE_DATA
  628.             Case giREADWRITE_DATABASE
  629.                 sSendCommand = gsSERVICE_LIB_CLASS & "." & gsSERVICE_READWRITE_DATA
  630.             Case giUSE_PROCESSOR_PERCENTAGE
  631.                 bRandomCommandRequired = True
  632.                 Randomize
  633.                 If Int((100 * Rnd) + 1) > giUseProcPercent Then
  634.                     'Don't use processor
  635.                     sSendCommand = gsSERVICE_LIB_CLASS & "." & gsSERVICE_DONT_USE_PROCESSOR
  636.                 Else
  637.                     'Use processor
  638.                     sSendCommand = gsSERVICE_LIB_CLASS & "." & gsSERVICE_USE_PROCESSOR
  639.                 End If
  640.         End Select
  641.     Else
  642.         sSendCommand = gsServiceCommand
  643.     End If
  644.     GetServiceCommand = sSendCommand
  645. End Function
  646.  
  647.  
  648. Function GetTestData(bSendSomething As Boolean, bReceiveSomething As Boolean, vSendData As Variant) As Boolean
  649.     Dim s As String
  650.     Dim i As Integer
  651.     Dim lSendNumRows As Long
  652.     Dim lSendRowSize As Long
  653.     Dim lReceiveNumRows As Long
  654.     Dim lReceiveRowSize As Long
  655.     Dim cData As Collection
  656.     Dim aData() As Variant
  657.     Dim lSendContainerType As Long
  658.     Dim lReceiveContainerType As Long
  659.     Dim bRandomDataRequired As Boolean
  660.     Dim lTaskDuration As Long
  661.     
  662.     lReceiveContainerType = glReceiveContainerType
  663.     lSendContainerType = glSendContainerType
  664.     
  665.     'Get Data that will be worked with
  666.     lSendNumRows = GetValueFromRange(gudtSendNumRows, bRandomDataRequired)
  667.     lSendRowSize = GetValueFromRange(gudtSendRowSize, bRandomDataRequired)
  668.     lReceiveNumRows = GetValueFromRange(gudtReceiveNumRows, bRandomDataRequired)
  669.     lReceiveRowSize = GetValueFromRange(gudtReceiveRowSize, bRandomDataRequired)
  670.     lTaskDuration = GetValueFromRange(gudtTaskDuration, bRandomDataRequired)
  671.     
  672.     'Check if we are sending or receiving any data
  673.     'Clear the data structures
  674.     bSendSomething = False
  675.     bReceiveSomething = False
  676.  
  677.     Set cData = New Collection
  678.     ReDim aData(0) As Variant
  679.     'Anything to send to the Service?
  680.     If (lSendNumRows = 0 Or lSendRowSize = 0) And (lReceiveNumRows = 0 Or lReceiveRowSize = 0) And lTaskDuration = 0 Then
  681.         'Nothing to send to the Service
  682.         bSendSomething = False
  683.     Else
  684.         bSendSomething = True
  685.         'Fill the data class send data for passing to the Service
  686.         s = Space(lSendRowSize)
  687.         Select Case lSendContainerType
  688.             Case giCONTAINER_TYPE_VARRAY
  689.                 ReDim Preserve aData(giRECORD_DATA_BEGIN + lSendNumRows - 1) As Variant
  690.                 For i = giRECORD_DATA_BEGIN To giRECORD_DATA_BEGIN + lSendNumRows - 1
  691.                     aData(i) = s
  692.                 Next i
  693.             Case giCONTAINER_TYPE_VCOLLECTION
  694.                 For i = 1 To lSendNumRows
  695.                     cData.Add s
  696.                 Next i
  697.          End Select
  698.     End If
  699.     'Anything to receive back from the Service?
  700.     If (lReceiveNumRows = 0 Or lReceiveRowSize = 0 Or lReceiveContainerType = giCONTAINER_TYPE_NULL) Then
  701.         bReceiveSomething = False
  702.         lReceiveNumRows = 0
  703.         lReceiveRowSize = 0
  704.         lReceiveContainerType = giCONTAINER_TYPE_NULL
  705.     Else
  706.         bReceiveSomething = True
  707.     End If
  708.     'Some data may actually be sent if something is expected back or a
  709.     'Milliseconds to be used is specified, but only enough data to instruct
  710.     'the Service on what to do.
  711.     If bReceiveSomething Or bSendSomething Then
  712.         'Fill the global data class receive parameters for passing to the Service
  713.         Select Case lSendContainerType
  714.         Case giCONTAINER_TYPE_VARRAY
  715.             'Make sure we have records in our array to fill
  716.             If UBound(aData) < giRECORD_DATA_BEGIN - 1 Then
  717.                 ReDim aData(giRECORD_DATA_BEGIN - 1) As Variant
  718.             End If
  719.             aData(giRECORD_NUMROWS) = lReceiveNumRows
  720.             aData(giRECORD_ROWSIZE) = lReceiveRowSize
  721.             aData(giRECORD_MILLISECONDS) = lTaskDuration
  722.             aData(giRECORD_CONTAINER_TYPE) = lReceiveContainerType
  723.         Case giCONTAINER_TYPE_VCOLLECTION
  724.             cData.Add lReceiveNumRows, CStr(giRECORD_NUMROWS)
  725.             cData.Add lReceiveRowSize, CStr(giRECORD_ROWSIZE)
  726.             cData.Add lTaskDuration, CStr(giRECORD_MILLISECONDS)
  727.             cData.Add lReceiveContainerType, CStr(giRECORD_CONTAINER_TYPE)
  728.         End Select
  729.     End If
  730.     
  731.     'Set return value and out parameters
  732.     Select Case lSendContainerType
  733.     Case giCONTAINER_TYPE_VARRAY
  734.         vSendData = aData()
  735.     Case giCONTAINER_TYPE_VCOLLECTION
  736.         Set vSendData = cData
  737.     End Select
  738.     GetTestData = bRandomDataRequired
  739. End Function
  740.  
  741. Sub ConfigureTest()
  742.     '-------------------------------------------------------------------------
  743.     'Purpose:   Configure the Client to run a test according to its current
  744.     '           properties.
  745.     'Effects:   U/I is reset for a new test
  746.     '           Remote Connection settings are made useing RacReg
  747.     '   [glCallsMade]
  748.     '           becomes 0
  749.     '   [glCallsReturned]
  750.     '           becomes 0
  751.     '   [gbTestInProcess]
  752.     '           becomes true
  753.     '   [gbStopping]
  754.     '           becomes false
  755.     '   [gcServices]
  756.     '           is destroyed and reinstanciated
  757.     '   [goTestTool]
  758.     '           is instanciated with the correct class having a RunTest method
  759.     'Assumption:
  760.     '           A test is not already in process
  761.     '-------------------------------------------------------------------------
  762.     'Configure test mode and connection settings
  763.     Dim iResult As Integer
  764.     
  765.     'Set the global status flags
  766.     'If there is reentry by a timer click exit sub
  767.     If gbTestInProcess Then Exit Sub
  768.     gbTestInProcess = True
  769.     gbStopping = False
  770.     'Clear the Services collection
  771.     Set gcServices = Nothing
  772.     Set gcServices = New Collection
  773.     'Set global variables
  774.     glCallsMade = 0
  775.     glCallsReturned = 0
  776.     'Display the stautus defaults
  777.     If gbShow Then
  778.         With frmClient
  779.             .lblCallsMade.Caption = 0
  780.             .lblCallsReturned.Caption = 0
  781.             .lblCallsMade.Refresh
  782.             .lblCallsReturned.Refresh
  783.         End With
  784.     End If
  785.     'Set the connection settings for AEWorker.Worker, AEQueueMgr.Queue, AEPoolMgr.Pool
  786.     With goRegClass
  787.         If gbConnectionRemote Then
  788.             If gbConnectionNetOLE Then
  789.                 iResult = .SetNetOLEServerSettings(True, "AEQueueMgr.Queue", , gsConnectionAddress)
  790.                 If iResult <> 0 Then GoTo ConfigureTest_RacRegError
  791.                 iResult = .SetNetOLEServerSettings(True, "AEWorker.Worker", , gsConnectionAddress)
  792.                 If iResult <> 0 Then GoTo ConfigureTest_RacRegError
  793.                 iResult = .SetNetOLEServerSettings(True, "AEPoolMgr.Pool", , gsConnectionAddress)
  794.                 If iResult <> 0 Then GoTo ConfigureTest_RacRegError
  795.             Else
  796.                 iResult = .SetAutoServerSettings(True, "AEQueueMgr.Queue", , gsConnectionAddress, gsConnectionProtocol, glConnectionAuthentication)
  797.                 If iResult <> 0 Then GoTo ConfigureTest_RacRegError
  798.                 iResult = .SetAutoServerSettings(True, "AEWorker.Worker", , gsConnectionAddress, gsConnectionProtocol, glConnectionAuthentication)
  799.                 If iResult <> 0 Then GoTo ConfigureTest_RacRegError
  800.                 iResult = .SetAutoServerSettings(True, "AEPoolMgr.Pool", , gsConnectionAddress, gsConnectionProtocol, glConnectionAuthentication)
  801.                 If iResult <> 0 Then GoTo ConfigureTest_RacRegError
  802.             End If
  803.         Else
  804.             iResult = .SetAutoServerSettings(False, "AEQueueMgr.Queue")
  805.             If iResult <> 0 Then GoTo ConfigureTest_RacRegError
  806.             iResult = .SetAutoServerSettings(False, "AEWorker.Worker")
  807.             If iResult <> 0 Then GoTo ConfigureTest_RacRegError
  808.             iResult = .SetAutoServerSettings(False, "AEPoolMgr.Pool")
  809.             If iResult <> 0 Then GoTo ConfigureTest_RacRegError
  810.         End If
  811.     End With
  812.     'Check our mode and create instances of the correct objects.
  813.     Select Case glModel
  814.         Case giMODEL_QUEUE
  815.             Set goTestTool = New clsQueueTestTool
  816.         Case giMODEL_DIRECT
  817.             Set goTestTool = New clsDirectTestTool
  818.         Case giMODEL_POOL
  819.             Set goTestTool = New clsPoolTestTool
  820.     End Select
  821.     Exit Sub
  822. ConfigureTest_RacRegError:
  823.     Err.Raise giCONNECTION_SETTING_FAILED, , ReplaceString(LoadResString(giCONNECTION_SETTING_FAILED), gsNAME_TOKEN, LoadResString(giRACREG_ERROR_CODE_OFFSET + iResult))
  824. End Sub
  825.  
  826. Sub StopOnError(sMessage As String)
  827.     '-------------------------------------------------------------------------
  828.     'Purpose:   Stop current test immediately
  829.     'Effects:
  830.     '           Calls goExplorer.Done
  831.     '   [glLastCallbackTick]
  832.     '           becomes value of GetTickCount
  833.     '   [goTestTool]    is destroyed
  834.     '   [gcServices]    is destroyed
  835.     '   [goExplorer]    is destroyed
  836.     '   [gbTestInProcess]
  837.     '           becomes false
  838.     '-------------------------------------------------------------------------
  839.     On Error GoTo StopOnError_Error
  840.     glLastCallbackTick = GetTickCount()
  841.     gbRunning = False
  842.     gbStopping = True   'This flags will cause callbacks to be ignored
  843.     If gbLog Then AddLogRecord 0, LoadResString(giSERVICES_POSTED), GetTickCount(), False
  844.     goExplorer.Done sMessage
  845.     Set goTestTool = Nothing
  846.     Set gcServices = Nothing
  847.     gbTestInProcess = False
  848.     Exit Sub
  849. StopOnError_Error:
  850.     If gbLog Then AddLogRecord 0, LoadResString(giSERVICES_POSTED), GetTickCount(), False
  851.     LogError Err
  852.     Resume Next
  853. End Sub
  854.  
  855. Public Sub CallBackHandler(lServiceID As Long, vServiceReturn As Variant, sServiceError As String)
  856.     '-------------------------------------------------------------------------
  857.     'Purpose:   Called by clsCallback Callback method or .
  858.     'IN:
  859.     '   [lServiceID]
  860.     '           Service Request ID
  861.     '   [vServiceReturn]
  862.     '           Data returned by Service Request
  863.     '   [sServiceError]
  864.     '           Error information for errors that occured processing Service Request.
  865.     '           Information is delimited by a semi-colon and a space in the following
  866.     '           format:  "number; source; description"
  867.     'Effects:
  868.     '           May call CompleteTest procedure if all ServiceRequest have been returned
  869.     '   [glCallsReturned]
  870.     '           Increments by one
  871.     '   [gcServices]
  872.     '           Removes respective item
  873.     '-------------------------------------------------------------------------
  874.     Dim lTicks As Long                      'Milliseconds
  875.     Dim oClientService As clsClientService  'Object storing Service Request information
  876.                                             'one will be removed from gcServices
  877.     Dim s As String
  878.     
  879.     On Error GoTo CallBackHandlerError
  880.     'Grab the tics, keep a global copy of the last callback tick count for statistics.
  881.     glLastCallbackTick = GetTickCount()
  882.     'Exit sub if Stopping test
  883.     If gbStopping Then Exit Sub
  884.     'Lookup the Service
  885.     If lServiceID > 0 Then
  886.        'This is a valid Service.
  887.         'Look up the ID in our collection.
  888.         Set oClientService = gcServices.Item(CStr(lServiceID))
  889.         'No error.  This Service is in our Service collection
  890.         'Increment the CallsReturned global
  891.         glCallsReturned = glCallsReturned + 1
  892.         If gbShow Then
  893.             With frmClient.lblCallsReturned
  894.                 .Caption = glCallsReturned
  895.                 .Refresh
  896.             End With
  897.         End If
  898.         If gbLog Then AddLogRecord lServiceID, LoadResString(giCALLBACK_RECEIVED), glLastCallbackTick, False
  899.         'Remove the Service from the collection
  900.         gcServices.Remove (CStr(lServiceID))
  901.     End If
  902.     If Len(sServiceError) > 0 Then
  903.         'It's an error message.  Log it.
  904.         'And abort test
  905.         s = LoadResString(giCALLBACK_ERROR_RECEIVED) & gsSEPERATOR & sServiceError
  906.         If gbLog Then AddLogRecord lServiceID, s, lTicks, False
  907.         StopOnError s
  908.         
  909.     End If
  910.     'Are we through with the test yet?
  911.     If glCallsReturned = glNumberOfCalls Then
  912.         'All Services have been queud and callbacks received.
  913.         If gbLog Then AddLogRecord 0, LoadResString(giCALLBACKS_COMPLETE), GetTickCount(), False
  914.         'Release the Explorer before running CompleteTest
  915.         gbRunCompleteProcedure = True
  916.         frmClient.tmrStartTest.Enabled = True
  917.     End If
  918.     Exit Sub
  919. CallBackHandlerError:
  920.     Select Case Err.Number
  921.         Case ERR_INVALID_PROCEDURE_CALL
  922.             'The ServiceID was not found in the Services collection.
  923.             LogError Err
  924.         Case ERR_OVER_FLOW
  925.             s = CStr(Err.Number) & gsSEPERATOR & Err.Source & gsSEPERATOR & Err.Description
  926.             glCallsReturned = 0
  927.             DisplayStatus Err.Description
  928.             If gbLog Then AddLogRecord 0, s, GetTickCount(), False
  929.         Case Else
  930.             'Do not raise an error back to the expediter
  931.             LogError Err
  932.     End Select
  933.     Exit Sub
  934. End Sub
  935.  
  936.