Getting a Return Code from an Application

Posted on 2003-02-19
Medium Priority
Last Modified: 2010-05-01
Below is the code I use to Launch a process then sit and listen for it to be finished..  I would like to get the true return code of the application I am executing.

It is always returning 0, and I have broken an application that if I were to use ws.run to launch it, it would return a non-zero. HOw can I get the true return code of the application that is finished executing..

The function I am launching is Launch.

Option Explicit

        hProcess As Long
        hThread As Long
        dwProcessId As Long
        dwThreadId As Long
End Type
        nLength As Long
        lpSecurityDescriptor As Long
        bInheritHandle As Long
End Type

        cb As Long
        lpReserved As String
        lpDesktop As String
        lpTitle As String
        dwX As Long
        dwY As Long
        dwXSize As Long
        dwYSize As Long
        dwXCountChars As Long
        dwYCountChars As Long
        dwFillAttribute As Long
        dwFlags As Long
        wShowWindow As Integer
        cbReserved2 As Integer
        lpReserved2 As Long
        hStdInput As Long
        hStdOutput As Long
        hStdError As Long
End Type

  cbSize As Long
  fMask As Long
  hwnd As Long
  lpVerb As String
  lpFile As String
  lpParameters As String
  lpDirectory As String
  nShow As Long
  hInstApp As Long
  lpIDList As Long
  lpClass As String
  hkeyClass As Long
  dwHotKey As Long
  hIcon As Long
  hProcess As Long
End Type

Const SW_HIDE = 0

Private Declare Function ShellExecuteEx Lib "shell32.dll" Alias "ShellExecuteExA" (lpExecInfo As _

Const SE_ERR_FNF = 2
Const WAIT_TIMEOUT = &H102

Private Const MAX_PATH = 260
Private Type FILETIME
        dwLowDateTime As Long
        dwHighDateTime As Long
End Type

Private Type WIN32_FIND_DATA
        dwFileAttributes As Long
        ftCreationTime As FILETIME
        ftLastAccessTime As FILETIME
        ftLastWriteTime As FILETIME
        nFileSizeHigh As Long
        nFileSizeLow As Long
        dwReserved0 As Long
        dwReserved1 As Long
        cFileName As String * MAX_PATH
        cAlternate As String * 14
End Type

Private Declare Function WaitForSingleObject Lib "kernel32" (ByVal hHandle As Long, ByVal dwMilliseconds As Long) As Long
Private Declare Function CreateProcess Lib "kernel32" Alias "CreateProcessA" _
        (ByVal lpApplicationName As String, ByVal lpCommandLine As String, ByVal _
         lpProcessAttributes As Long, ByVal lpThreadAttributes As Long, _
         ByVal bInheritHandles As Long, ByVal dwCreationFlags As Long, _
         ByVal lpEnvironment As Long, ByVal lpCurrentDirectory As String, _
         lpStartupInfo As STARTUPINFO, lpProcessInformation As _
Private Declare Function GetExitCodeProcess Lib "kernel32" (ByVal hProcess As Long, lpExitCode As Long) As Long
Private Declare Function CloseHandle Lib "kernel32" (ByVal hObject As Long) As Long
Private Declare Function FormatMessage Lib "kernel32" Alias "FormatMessageA" (ByVal dwFlags As Long, lpSource As Any, ByVal dwMessageId As Long, ByVal dwLanguageId As Long, ByVal lpBuffer As String, ByVal nSize As Long, Arguments As Long) As Long

' ***************************************************************************************
Private LaunchReturnCode As Long ' Return code from launching and running an application
'Private Const INFINITE = &HFFFF

Private Const WAIT_ABANDONED = &H80
Private Const WAIT_OBJECT_0 = 0
'Private Const WAIT_TIMEOUT = &H102

Public Function Launch(Program As String, ProgParams As String, retval As Long, Msg As String) As Boolean

On Error GoTo Launch_Error

  Dim sei As SHELLEXECUTEINFO  ' structure used by the function
  'Dim retval As Long  ' return value
  ' Load the information needed to open C:\Docs\readme.txt
  ' into the structure.
  With sei
      ' Size of the structure
      .cbSize = Len(sei)
      ' Use the optional hProcess element of the structure.
      ' Handle to the window calling this function.
      .hwnd = frmReboot.hwnd
      ' The action to perform: open the file.
      .lpVerb = "open"
      ' The file to open.
      .lpFile = Program
      ' No additional parameters are needed here.
      .lpParameters = ProgParams
      ' The default directory -- not really necessary in this case.
      .lpDirectory = TargetDirectory
      ' Simply display the window.
      .nShow = SW_HIDE
      ' The other elements of the structure are either not used
      ' or will be set when the function returns.
  End With
  ' Open the file using its associated program.
  retval = ShellExecuteEx(sei)
  MsgBox retval
  If retval = 0 Then
      ' The function failed, so report the error.  Err.LastDllError
      ' could also be used instead, if you wish.
      Select Case sei.hInstApp
      Case SE_ERR_FNF
          MsgBox "File not found"
           MsgBox "no program is associated to this file"
      Case Else
          MsgBox "An unexpected error occured."
      End Select
      ' Wait for the opened process to close before continuing.  Instead
      ' of waiting once for a time of INFINITE, this example repeatedly checks to see if the
      ' is still open.  This allows the DoEvents VB function to be called, preventing
      ' our program from appearing to lock up while it waits.
          retval = WaitForSingleObject(sei.hProcess, 0)
      Loop While retval = WAIT_TIMEOUT
      MsgBox retval
  End If

Exit Function


Msg = "LAUNCH ERROR: " & Err.Description
Launch = False
Exit Function

End Function
Question by:tchous
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
1 Comment

Accepted Solution

webJose earned 400 total points
ID: 7989657
Also use this flag:

Private Const SEE_MASK_FLAG_DDEWAIT As Long = &H100

Also, in the case of retval <> 0 (the function ShellExecuteex succeeded), you must check for sei.hInstApp.  If it is less than or equal to 32, the process was not shelled.

Finally, after the wait loop you must call GetExitCodeProcess to get the return code you are looking for.

Featured Post

Free Tool: SSL Checker

Scans your site and returns information about your SSL implementation and certificate. Helpful for debugging and validating your SSL configuration.

One of a set of tools we are providing to everyone as a way of saying thank you for being a part of the community.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

The debugging module of the VB 6 IDE can be accessed by way of the Debug menu item. That menu item can normally be found in the IDE's main menu line as shown in this picture.   There is also a companion Debug Toolbar that looks like the followin…
Since upgrading to Office 2013 or higher installing the Smart Indenter addin will fail. This article will explain how to install it so it will work regardless of the Office version installed.
As developers, we are not limited to the functions provided by the VBA language. In addition, we can call the functions that are part of the Windows operating system. These functions are part of the Windows API (Application Programming Interface). U…
Get people started with the process of using Access VBA to control Outlook using automation, Microsoft Access can control other applications. An example is the ability to programmatically talk to Microsoft Outlook. Using automation, an Access applic…
Suggested Courses

770 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question