run a process in background on Windows

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Hello,
there are several tips how to run a child process ($cmd) in background on Windows. Firstly I used popen:
|function execInBackground($cmd)
{
$cmd = 'start /B "" ' . $cmd;
pclose(popen($cmd, "r"));
}

Using of popen has unexpected side effect. If somebody locks a file, the child process inherits the file lock Windows handle and the file is locked by the child process. The child process application don't know about it.

I needed to call a child simple http server that wraps the java code and I made a file locks in php to make a critical section for launching the simple java http server. And the lock is held forever by the java child process.

This problem is caused by the inherit_handle parameter set to TRUE in CreateProcess function in the proc_open Windows implementation.

This problem is more probable. If someone uses log4php the log files are file locked and the child process holds the logs. So the logs cannot be deleted etc.

I also tried to use
function execInBackground($cmd)
{
   $cmd = "c:\tmp\PSTools\PsExec.exe -d ".$cmd;
   exec($cmd);
}
This implementation doesn't have problem with file locks as described above but opens a console window for a child process.

So I had to write my PsExec.exe equivalent in c++:
int main(int argc, char **argv)
{
  DWORD cpError = ERROR_SUCCESS;
  if (argc>1)
  {
    std::string cmdline = argv[1];
    for (int i=2; i<argc; i++)
    {
      cmdline=cmdline+" "+argv[i];
    }

    STARTUPINFO si;
    PROCESS_INFORMATION pi;

    ZeroMemory( &si, sizeof(si) );
    si.cb = sizeof(si);
    ZeroMemory( &pi, sizeof(pi) );

    // Start the child process.
    if( !CreateProcess( NULL,   // No module name (use command line).
      (LPSTR)cmdline.c_str(), // Command line.
      NULL,             // Process handle not inheritable.
      NULL,             // Thread handle not inheritable.
      FALSE,            // Set handle inheritance to FALSE.
      CREATE_NO_WINDOW, // Creation flags.
      NULL,             // Use parent's environment block.
      NULL,             // Use parent's starting directory.
      &si,              // Pointer to STARTUPINFO structure.
      &pi )             // Pointer to PROCESS_INFORMATION structure.
      )
    {
      cpError = GetLastError();
      printf( "CreateProcess failed (%d).\n", cpError );
      return 1;
    }

    // DONT wait until child process exits.
    //WaitForSingleObject( pi.hProcess, INFINITE );

    // Close process and thread handles.
    CloseHandle( pi.hProcess );
    CloseHandle( pi.hThread );
  }

  return cpError;
}|

I think It would be nice to have a function exec_in_background(.) that does it directly in the php core.
Jan.

[Index of Archives]     [PHP Home]     [Apache Users]     [PHP on Windows]     [Kernel Newbies]     [PHP Install]     [PHP Classes]     [Pear]     [Postgresql]     [Postgresql PHP]     [PHP on Windows]     [PHP Database Programming]     [PHP SOAP]

  Powered by Linux