Results 1 to 8 of 8

Thread: WaitForSingleObject Help?

  1. #1

    Thread Starter
    New Member
    Join Date
    Mar 2007
    Posts
    4

    WaitForSingleObject Help?

    I have written a small app in VB6 that copies a Microsoft Access database application to the local C drive and runs it. It then uses WaitForSingleObject to halt program execution until the user exits the Access database then it deletes the temporary copy of the Access DB from the C drive.

    Unfortunately the WaitForSingleObject call also seems to prevent the user from opening other Office documents.

    Does anyone know a way to fix this?

    Cheers.

  2. #2
    I'm about to be a PowerPoster! Hack's Avatar
    Join Date
    Aug 2001
    Location
    Searching for mendhak
    Posts
    58,333

    Re: WaitForSingleObject Help?

    Quote Originally Posted by btonkinson
    Unfortunately the WaitForSingleObject call also seems to prevent the user from opening other Office documents.
    Welcome to the forums.

    What happens when they attempt to open these documents?

    Is it across the board for all Office products (Word, Excel, etc) or does it only affect one?

  3. #3

    Thread Starter
    New Member
    Join Date
    Mar 2007
    Posts
    4

    Re: WaitForSingleObject Help?

    Hi thanks

    It doesn't appear to effect text files that open in notepad but it does effect Excel and Word files. Furthermore I have realised that they do open it just takes a very, very long time.

    If during this time I end the loader.exe task the Excel / Word file opens immediatly.

    Think it is related to this problem: "Use caution when calling the wait functions and code that directly or indirectly creates windows. If a thread creates any windows, it must process messages. Message broadcasts are sent to all windows in the system. A thread that uses a wait function with no time-out interval may cause the system to become deadlocked." - quoted from:

    http://msdn2.microsoft.com/en-us/library/ms687032.aspx

    Brian

  4. #4
    I'm about to be a PowerPoster! Hack's Avatar
    Join Date
    Aug 2001
    Location
    Searching for mendhak
    Posts
    58,333

    Re: WaitForSingleObject Help?

    Quote Originally Posted by btonkinson
    Think it is related to this problem: "Use caution when calling the wait functions and code that directly or indirectly creates windows. If a thread creates any windows, it must process messages. Message broadcasts are sent to all windows in the system. A thread that uses a wait function with no time-out interval may cause the system to become deadlocked."
    And this is exactly what sounds like is happening.

    Since this is in VB6, perhaps tossing a DoEvents into your code to let your OS do some processing would help.

  5. #5

    Thread Starter
    New Member
    Join Date
    Mar 2007
    Posts
    4

    Re: WaitForSingleObject Help?

    Where would you suggest I put the doEvents command?

    Code:
    Public Sub ShellAndWait(ByVal program_name As String, ByVal window_style As VbAppWinStyle)
    Dim process_id As Long
    Dim process_handle As Long
    
        ' Start the program.
        On Error GoTo ShellError
        process_id = Shell(program_name, window_style)
        On Error GoTo 0
    
        DoEvents
    
        ' Wait for the program to finish.
        ' Get the process handle.
        process_handle = OpenProcess(SYNCHRONIZE, 0, process_id)
    
        If process_handle <> 0 Then
            WaitForSingleObject process_handle, INFINITE
            CloseHandle process_handle
        End If
    
    Exit Sub
    If I put it in before WaitForSingleObject process_handle, INFINITE then won't it only process events before the wait period and equally after it only events after it has stopped waiting?

    I am happy to look at other ways of halting program execution until the started app has been closed if you know of any?

    Thanks for your help.

  6. #6
    Fanatic Member schoolbusdriver's Avatar
    Join Date
    Jan 2006
    Location
    O'er yonder
    Posts
    1,020

    Re: WaitForSingleObject Help?

    Don't know if this little snippet will give you an idea. It's part of a registry monitoring routine, but demonstrates how you can use WaitForSingleObject in combination with DoEvents in a While-Wend loop. You can just Exit Sub to get out of the loop. Although TaskManager shows 100% CPU usage, neither the app, other progs nor the PC freeze or seem to slow down. It's quite efficient for all that.

    Code:
    'Watch a registry change by looking at KeyChanged.
       While DoEvents
          KeyChanged = WaitForSingleObject(hEvent, TimeOutInterval) = WAIT_OBJECT_0 'Cast the initial value.
          If KeyChanged = True Then 'Start watching for changes.
             RegNotifyChangeKeyValue hkey, WatchSubTree, REG_NOTIFY_CHANGE_LAST_SET, hEvent, True
             With frmRegMon.txtMsgs
    'The key has already been checked for errors.
                NewValue = GetDataAsString(hKeyType, strSubKey, strKeyName, "New")
                If NewValue <> OldValue Then 'Test for a change.
    'Dump the results to the text box.
                   .Text = .Text & vbCrLf & "Key change detected at " & Time$ & "."
                   .Text = .Text & vbCrLf & "Old Value = " & OldValue
                   .Text = .Text & vbCrLf & "New Value = " & NewValue
                Else
                   .Text = .Text & vbCrLf & "A change was detected in another key's value"
                End If
                OldValue = NewValue 'Reset the initial value to test.
             End With
          End If
       Wend
    Edit: Const WAIT_OBJECT_0 = 0
    Last edited by schoolbusdriver; Mar 6th, 2007 at 04:38 AM.

  7. #7

    Thread Starter
    New Member
    Join Date
    Mar 2007
    Posts
    4

    Re: WaitForSingleObject Help?

    Thanks schoolbusdriver - that gave me a bit of inspiration. I have come up with this which seems to solve the problem:

    Code:
    Public Sub ShellAndWait(ByVal program_name As String, ByVal window_style As VbAppWinStyle)
    Dim process_id As Long
    Dim process_handle As Long
    Dim procState As Long
    Dim counter As Long
    
        ' Start the program.
        On Error GoTo ShellError
        process_id = Shell(program_name, window_style)
        On Error GoTo 0
    
        DoEvents
    
        ' Wait for the program to finish.
        ' Get the process handle.
        process_handle = OpenProcess(SYNCHRONIZE, 0, process_id)
    
        If process_handle <> 0 Then
            procState = 258
            counter = 0
            While procState = 258
                If counter = 10000 Then
                    ' Only check procState every 10,000 runs - saves on hogging CPU
                    procState = WaitForSingleObject(process_handle, 1)
                    counter = 0
                Else
                    counter = counter + 1
                End If
                DoEvents
            Wend
            CloseHandle process_handle
        End If
    
    Exit Sub
    
    ShellError:
        MsgBox "Error starting task " & _
            program_name & vbCrLf & _
            Err.Description, vbOKOnly Or vbExclamation, _
            "Error" & Err.Number
    End Sub
    However This is still showing as 100% CPU usage on task manager (due to the counting in the loop). Any ideas? I really want this program to just sit in the background and do nothing until the SHELLed app finishes.

  8. #8
    Fanatic Member schoolbusdriver's Avatar
    Join Date
    Jan 2006
    Location
    O'er yonder
    Posts
    1,020

    Re: WaitForSingleObject Help?

    The usual way to reduce processor usage is to introduce a "Sleep" into the loop. You can do this just before the Wend, ie "Sleep 250" (milliseconds). You may want to change the counter from 10000 as well. Somewhere along the line you should get a happy balance.

    There has been some discussion of other various ways to reduce CPU time etc. Take a look at http://www.vbforums.com/showthread.p...light=doevents. Take care if you run the code I posted - if you run it via the IDE, it doesn't exit correctly. However when it's compiled, it seems to work fine.

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  



Click Here to Expand Forum to Full Width