home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 10 Tools / 10-Tools.zip / wxos2233.zip / wxOS2-2_3_3.zip / wxWindows-2.3.3 / src / os2 / utilsexc.cpp < prev    next >
C/C++ Source or Header  |  2002-03-24  |  8KB  |  274 lines

  1. /////////////////////////////////////////////////////////////////////////////
  2. // Name:        utilsexec.cpp
  3. // Purpose:     Various utilities
  4. // Author:      David Webster
  5. // Modified by:
  6. // Created:     10/17/99
  7. // RCS-ID:      $Id: UTILSEXC.CPP,v 1.15 2002/03/23 01:31:21 VZ Exp $
  8. // Copyright:   (c) David Webster
  9. // Licence:     wxWindows license
  10. /////////////////////////////////////////////////////////////////////////////
  11.  
  12. // For compilers that support precompilation, includes "wx.h".
  13. #include "wx/wxprec.h"
  14.  
  15. #ifndef WX_PRECOMP
  16. #include "wx/setup.h"
  17. #include "wx/utils.h"
  18. #include "wx/app.h"
  19. #include "wx/intl.h"
  20. #endif
  21.  
  22. #include "wx/log.h"
  23.  
  24. #include "wx/process.h"
  25.  
  26. #include "wx/os2/private.h"
  27.  
  28. #define PURE_32
  29. #ifndef __EMX__
  30. #include <upm.h>
  31. #include <netcons.h>
  32. #include <netbios.h>
  33. #endif
  34.  
  35. #include <ctype.h>
  36. #ifdef __EMX__
  37. #include <dirent.h>
  38. #endif
  39.  
  40. #include <sys/stat.h>
  41. #include <io.h>
  42.  
  43. #include <stdio.h>
  44. #include <stdlib.h>
  45. #include <string.h>
  46. #include <errno.h>
  47. #include <stdarg.h>
  48.  
  49.  
  50. // this message is sent when the process we're waiting for terminates
  51. #define wxWM_PROC_TERMINATED (WM_USER + 10000)
  52.  
  53. #ifndef NO_ERROR
  54. #  define NO_ERROR  0
  55. #endif
  56.  
  57. // structure describing the process we're being waiting for
  58. struct wxExecuteData
  59. {
  60. public:
  61.     ~wxExecuteData()
  62.     {
  63. //         cout << "Closing thread: " << endl;
  64.         DosExit(EXIT_PROCESS, 0);
  65.     }
  66.  
  67.     HWND                            hWnd;          // window to send wxWM_PROC_TERMINATED to [not used]
  68.     RESULTCODES                     vResultCodes;
  69.     wxProcess*                      pHandler;
  70.     ULONG                           ulExitCode;    // the exit code of the process
  71.     bool                            bState;        // set to FALSE when the process finishes
  72. };
  73.  
  74. static ULONG wxExecuteThread(
  75.   wxExecuteData*                    pData
  76. )
  77. {
  78.     ULONG                           ulRc;
  79.     PID                             vPidChild;
  80.  
  81. //     cout << "Executing thread: " << endl;
  82.  
  83.     ulRc = ::DosWaitChild( DCWA_PROCESSTREE
  84.                           ,DCWW_NOWAIT
  85.                           ,&pData->vResultCodes
  86.                           ,&vPidChild
  87.                           ,pData->vResultCodes.codeTerminate // process PID to look at
  88.                          );
  89.     if (ulRc != NO_ERROR)
  90.     {
  91.         wxLogLastError("DosWaitChild");
  92.     }
  93.     delete pData;
  94.     return 0;
  95. }
  96.  
  97. // window procedure of a hidden window which is created just to receive
  98. // the notification message when a process exits
  99. MRESULT APIENTRY wxExecuteWindowCbk(
  100.   HWND                              hWnd
  101. , ULONG                             ulMessage
  102. , MPARAM                            wParam
  103. , MPARAM                            lParam
  104. )
  105. {
  106.     if (ulMessage == wxWM_PROC_TERMINATED)
  107.     {
  108.         wxExecuteData*              pData = (wxExecuteData *)lParam;
  109.  
  110.         if (pData->pHandler)
  111.         {
  112.             pData->pHandler->OnTerminate( (int)pData->vResultCodes.codeTerminate
  113.                                          ,(int)pData->vResultCodes.codeResult
  114.                                         );
  115.         }
  116.  
  117.         if (pData->bState)
  118.         {
  119.             // we're executing synchronously, tell the waiting thread
  120.             // that the process finished
  121.             pData->bState = 0;
  122.         }
  123.         else
  124.         {
  125.             // asynchronous execution - we should do the clean up
  126.             delete pData;
  127.         }
  128.         ::WinDestroyWindow(hWnd);    // we don't need it any more
  129.     }
  130.     return 0;
  131. }
  132.  
  133. long wxExecute(
  134.   const wxString&                   rCommand
  135. , int                               flags
  136. , wxProcess*                        pHandler
  137. )
  138. {
  139.     if (rCommand.IsEmpty())
  140.     {
  141. //         cout << "empty command in wxExecute." << endl;
  142.         return 0;
  143.     }
  144.  
  145.     // create the process
  146.     UCHAR                           vLoadError[CCHMAXPATH] = {0};
  147.     RESULTCODES                     vResultCodes = {0};
  148.     ULONG                           ulExecFlag;
  149.     PSZ                             zArgs = NULL;
  150.     PSZ                             zEnvs = NULL;
  151.     ULONG                           ulWindowId;
  152.     APIRET                          rc;
  153.     PFNWP                           pOldProc;
  154.     TID                             vTID;
  155.  
  156.     if (flags & wxEXEC_SYNC)
  157.         ulExecFlag = EXEC_SYNC;
  158.     else
  159.         ulExecFlag = EXEC_ASYNCRESULT;
  160.  
  161.     rc = ::DosExecPgm( (PCHAR)vLoadError
  162.                       ,sizeof(vLoadError)
  163.                       ,ulExecFlag
  164.                       ,zArgs
  165.                       ,zEnvs
  166.                       ,&vResultCodes
  167.                       ,(PSZ)rCommand.c_str()
  168.                      );
  169.     if (rc != NO_ERROR)
  170.     {
  171.         wxLogSysError(_("Execution of command '%s' failed with error: %ul"), rCommand.c_str(), rc);
  172.         return 0;
  173.     }
  174. //     cout << "Executing: " << rCommand.c_str() << endl;
  175.     // Alloc data
  176.     wxExecuteData*                  pData = new wxExecuteData;
  177.  
  178.     pData->vResultCodes = vResultCodes;
  179.     pData->hWnd         = NULLHANDLE;
  180.     pData->bState       = (flags & wxEXEC_SYNC) != 0;
  181.     if (flags & wxEXEC_SYNC)
  182.     {
  183.         wxASSERT_MSG(!pHandler, wxT("wxProcess param ignored for sync execution"));
  184.         pData->pHandler = NULL;
  185.     }
  186.     else
  187.     {
  188.         // may be NULL or not
  189.         pData->pHandler = pHandler;
  190.     }
  191.  
  192.     rc = ::DosCreateThread( &vTID
  193.                            ,(PFNTHREAD)&wxExecuteThread
  194.                            ,(ULONG)pData
  195.                            ,CREATE_READY|STACK_SPARSE
  196.                            ,8192
  197.                           );
  198.     if (rc != NO_ERROR)
  199.     {
  200.         wxLogLastError("CreateThread in wxExecute");
  201.         delete pData;
  202.  
  203.         // the process still started up successfully...
  204.         return vResultCodes.codeTerminate;
  205.     }
  206.     if (!(flags & wxEXEC_SYNC))
  207.     {
  208.         // return the pid
  209.         // warning: don't exit your app unless you actively
  210.         // kill and cleanup you child processes
  211.         // Maybe detach the process here???
  212.         // If cmd.exe need to pass DETACH to detach the process here
  213.         return vResultCodes.codeTerminate;
  214.     }
  215.  
  216.     // waiting until command executed
  217.     ::DosWaitThread(&vTID, DCWW_WAIT);
  218.  
  219.     ULONG ulExitCode = pData->vResultCodes.codeResult;
  220.     delete pData;
  221.  
  222.     // return the exit code
  223.     return (long)ulExitCode;
  224. }
  225.  
  226. long wxExecute(
  227.   char**                            ppArgv
  228. , int                               flags
  229. , wxProcess*                        pHandler
  230. )
  231. {
  232.     wxString                        sCommand;
  233.  
  234.     while (*ppArgv != NULL)
  235.     {
  236.         sCommand << *ppArgv++ << ' ';
  237.     }
  238.     sCommand.RemoveLast();
  239.     return wxExecute( sCommand
  240.                      ,flags
  241.                      ,pHandler
  242.                     );
  243. }
  244.  
  245. bool wxGetFullHostName(
  246.   wxChar*                           zBuf
  247. , int                               nMaxSize
  248. )
  249. {
  250. #if wxUSE_NET_API
  251.     char                            zServer[256];
  252.     char                            zComputer[256];
  253.     unsigned long                   ulLevel = 0;
  254.     unsigned char*                  zBuffer = NULL;
  255.     unsigned long                   ulBuffer = 256;
  256.     unsigned long*                  pulTotalAvail = NULL;
  257.  
  258.     NetBios32GetInfo( (const unsigned char*)zServer
  259.                      ,(const unsigned char*)zComputer
  260.                      ,ulLevel
  261.                      ,zBuffer
  262.                      ,ulBuffer
  263.                      ,pulTotalAvail
  264.                     );
  265.     strncpy(zBuf, zComputer, nMaxSize);
  266.     zBuf[nMaxSize] = _T('\0');
  267. #else
  268.     strcpy(zBuf, "noname");
  269. #endif
  270.     return *zBuf ? TRUE : FALSE;
  271.     return TRUE;
  272. }
  273.  
  274.