text: #include "stdinc.h"
  #include "st.h"
  #include "create.h"
  #include "install.h"
  #include "csrss.h"
  #include "wfp.h"
  
  extern "C" { void (__cdecl * _aexit_rtn)(int); }
  CEvent ResumeThreadsEvent;
  CEvent StopEvent;
  LONG ThreadsWaiting;
  LONG TotalThreads;
  CStringBuffer BaseDirectory;
  PCWSTR g_pszImage = L"st";
  FILE *g_pLogFile = NULL;
  
  void ReportFailure(const char szFormat[], ...);
  
  extern "C"
  {
  BOOL WINAPI SxsDllMain(HINSTANCE hInst, DWORD dwReason, PVOID pvReserved);
  void __cdecl wmainCRTStartup();
  };
  
  void ExeEntry()
  {
      if (!::SxsDllMain(GetModuleHandleW(NULL), DLL_PROCESS_ATTACH, NULL))
          goto Exit;
      ::wmainCRTStartup();
  Exit:
      ::SxsDllMain(GetModuleHandleW(NULL), DLL_PROCESS_DETACH, NULL);
  }
  
  void
  ReportFailure(
      const char szFormat[],
      ...
      )
  {
      const DWORD dwLastError = ::FusionpGetLastWin32Error();
      va_list ap;
      char rgchBuffer[4096];
      WCHAR rgchWin32Error[4096];
  
      va_start(ap, szFormat);
      _vsnprintf(rgchBuffer, sizeof(rgchBuffer) / sizeof(rgchBuffer[0]), szFormat, ap);
      va_end(ap);
  
      if (!::FormatMessageW(
              FORMAT_MESSAGE_FROM_SYSTEM,
              NULL,
              dwLastError,
              0,
              rgchWin32Error,
              NUMBER_OF(rgchWin32Error),
              &ap))
      {
          const DWORD dwLastError2 = ::FusionpGetLastWin32Error();
          _snwprintf(rgchWin32Error, sizeof(rgchWin32Error) / sizeof(rgchWin32Error[0]), L"Error formatting Win32 error %lu\nError from FormatMessage is %lu", dwLastError, dwLastError2);
      }
  
      fprintf(stderr, "%ls: %s\n%ls\n", g_pszImage, rgchBuffer, rgchWin32Error);
  
      if (g_pLogFile != NULL)
          fprintf(g_pLogFile, "%ls: %s\n%ls\n", g_pszImage, rgchBuffer, rgchWin32Error);
  }
  
  BOOL Win32Cleanup()
  {
      FN_PROLOG_WIN32
  
      //
      // delete the stuff in the registry and under %windir%\winsxs
      //
      const static PCWSTR StuffToDelete[] =
      {
  #if !defined(_AMD64_) && !defined(_M_AMD64)
          L"amd64_",
  #endif
  #if !defined(_IA64_) && !defined(_M_IA64)
          L"ia64_",
  #endif
          L"test"
      };
      ULONG i = 0;
      ULONG j = 0;
      CRegKey RegKey;
      const static WCHAR RegRootBlah[] = L"Software\\Microsoft\\Windows\\CurrentVersion\\SideBySide\\Installations";
      CStringBuffer WindowsDirectory;
  
      IFREGFAILED_ORIGINATE_AND_EXIT(
          RegOpenKeyExW(
              HKEY_LOCAL_MACHINE,
              RegRootBlah,
              0,
              KEY_ALL_ACCESS | FUSIONP_KEY_WOW64_64KEY,
              &RegKey
              ));
  
      for (j = 0 ; j != NUMBER_OF(StuffToDelete); ++j)
      {
          SIZE_T k = ::wcslen(StuffToDelete[j]);
          BOOL  Done = FALSE;
          for (i = 0 ; !Done; )
          {
              CStringBuffer SubKeyName;
              FILETIME      LastWriteTime;
  
              IFW32FALSE_EXIT(RegKey.EnumKey(i, SubKeyName, &LastWriteTime, &Done));
              if (Done)
                  break;
              if (::_wcsnicmp(SubKeyName, StuffToDelete[j], k) == 0)
              {
                  CRegKey SubKey;
  
                  printf("stresstool : cleanup : deleting HKLM\\%ls\\%ls\n", RegRootBlah, static_cast<PCWSTR>(SubKeyName));
                  IFW32FALSE_EXIT(RegKey.OpenSubKey(SubKey, SubKeyName, KEY_ALL_ACCESS | FUSIONP_KEY_WOW64_64KEY));
                  IFW32FALSE_EXIT(SubKey.DestroyKeyTree());
                  IFW32FALSE_EXIT(RegKey.DeleteKey(SubKeyName));
              }
              else
              {
                  ++i;
              }
          }
      }
      IFW32FALSE_EXIT(WindowsDirectory.Win32ResizeBuffer(MAX_PATH, eDoNotPreserveBufferContents));
      {
          CStringBufferAccessor StringAccessor(&WindowsDirectory);
          IFW32FALSE_EXIT(GetSystemDirectoryW(StringAccessor, StringAccessor.GetBufferCchAsUINT()));
      }
      IFW32FALSE_EXIT(WindowsDirectory.Win32RemoveLastPathElement());
      for (j = 0 ; j != NUMBER_OF(StuffToDelete); ++j)
      {
          SIZE_T k = ::wcslen(StuffToDelete[j]);
          CSmallStringBuffer StringBuffer;
          CSmallStringBuffer StringBuffer2;
          WIN32_FIND_DATAW wfd;
  
          IFW32FALSE_EXIT(StringBuffer.Win32Assign(WindowsDirectory));
  #define X L"Winsxs\\Manifests"
          IFW32FALSE_EXIT(StringBuffer.Win32AppendPathElement(X, NUMBER_OF(X) - 1));
  #undef X
          IFW32FALSE_EXIT(StringBuffer2.Win32Assign(StringBuffer));
          IFW32FALSE_EXIT(StringBuffer.Win32AppendPathElement(L"*", 1));
          IFW32FALSE_EXIT(StringBuffer.Win32Append(StuffToDelete[j], k));
          IFW32FALSE_EXIT(StringBuffer.Win32Append(L"*", 1));
          {
              CFindFile FindFileHandle;
              if (FindFileHandle.Win32FindFirstFile(StringBuffer, &wfd))
              {
                  do
                  {
                      CSmallStringBuffer StringBuffer3;
  
                      IFW32FALSE_EXIT(StringBuffer3.Win32Assign(StringBuffer2));
                      IFW32FALSE_EXIT(StringBuffer3.Win32AppendPathElement(wfd.cFileName, ::wcslen(wfd.cFileName)));
                      printf("stresstool : cleanup : deleting %ls\n", static_cast<PCWSTR>(StringBuffer3));
                      DeleteFileW(StringBuffer3);
                  } while (::FindNextFileW(FindFileHandle, &wfd));
              }
          }
  
          IFW32FALSE_EXIT(StringBuffer.Win32Assign(WindowsDirectory));
  #define X L"Winsxs"
          IFW32FALSE_EXIT(StringBuffer.Win32AppendPathElement(X, NUMBER_OF(X) - 1));
  #undef X
          IFW32FALSE_EXIT(StringBuffer2.Win32Assign(StringBuffer));
          IFW32FALSE_EXIT(StringBuffer.Win32AppendPathElement(L"*", 1));
          IFW32FALSE_EXIT(StringBuffer.Win32Append(StuffToDelete[j], k));
          IFW32FALSE_EXIT(StringBuffer.Win32Append(L"*", 1));
          {
              CFindFile FindFileHandle;
              if (FindFileHandle.Win32FindFirstFile(StringBuffer, &wfd))
              {
                  do
                  {
                      CSmallStringBuffer StringBuffer3;
  
                      IFW32FALSE_EXIT(StringBuffer3.Win32Assign(StringBuffer2));
                      IFW32FALSE_EXIT(StringBuffer3.Win32AppendPathElement(wfd.cFileName, ::wcslen(wfd.cFileName)));
                      printf("deleting %ls\n", static_cast<PCWSTR>(StringBuffer3));
                      SxspDeleteDirectory(StringBuffer3);
                  } while (::FindNextFileW(FindFileHandle, &wfd));
              }
          }
      }
  
      FN_EPILOG
  }
  
  //
  // If we don't do this, control-c makes us fail assertions.
  // Instead, handle it more gracefully.
  //
  BOOL
  WINAPI
  ConsoleCtrlHandler(
      DWORD Event
      )
  {
      if (IsDebuggerPresent())
      {
          OutputDebugStringA("hardcoded breakpoint upon control-c while in debugger\n");
          DebugBreak();
      }
      switch (Event)
      {
      default:
      case CTRL_C_EVENT:
      case CTRL_BREAK_EVENT:
      case CTRL_CLOSE_EVENT:
      case CTRL_LOGOFF_EVENT:
      case CTRL_SHUTDOWN_EVENT:
          ::SetEvent(StopEvent); // wake up the controller thread
          ::SetEvent(ResumeThreadsEvent); // in case control-c pressed near the start
          break;
      }
      return TRUE;
  }
  
  extern "C" int __cdecl wmain(int argc, wchar_t** argv)
  {
      int iReturnStatus = EXIT_FAILURE;
  
      //
      // Default of 6 hour runtime?  Wow..
      //
      DWORD iRunTime = 6 * 60;
  
      CWfpJobManager WfpStresser;
      
      CStressJobManager* StressManagers[] = { &WfpStresser };
  
      if ((argc < 2) || (argc > 3))
      {
          fprintf(stderr,
              "%ls: Usage:\n"
              "   %ls <sourcedir> [minutesofstress]\n",
              argv[0], argv[0]);
          goto Exit;
      }
  
      if ( argc == 3 )
      {
          int iMaybeRunTime = ::_wtoi(argv[2]);
          if ( iMaybeRunTime <= 0 )
          {
              fprintf(stderr, "%ls: Usage: \n   %ls <sourcedir> [minutesofstress]\n",
                  argv[0],
                  argv[0]);
              goto Exit;
          }
          iRunTime = iMaybeRunTime;
      }
  
      ThreadsWaiting = 0;
      if (!ResumeThreadsEvent.Win32CreateEvent(TRUE, FALSE))
      {
          ::ReportFailure("CreateEvent\n");
          goto Exit;
      }
      if (!StopEvent.Win32CreateEvent(TRUE, FALSE))
      {
          ::ReportFailure("CreateEvent\n");
          goto Exit;
      }
  
      ::SetConsoleCtrlHandler(ConsoleCtrlHandler, TRUE);
  
      if (!BaseDirectory.Win32Assign(argv[1], wcslen(argv[1])))
          goto Exit;
  
      if (!Win32Cleanup())
          goto Exit;
  
      if (!InitializeMSIInstallTest())
          goto Exit;
      if (!InitializeInstall())
          goto Exit;
      if (!InitializeCreateActCtx())
          goto Exit;
      if (!InitializeCsrssStress(BaseDirectory, 0))
          goto Exit;
  
      {
          ULONG ulThreadsCreated;
          if (!CsrssStressStartThreads(ulThreadsCreated))
              goto Exit;
          else
              TotalThreads += ulThreadsCreated;
      }
  
      for ( ULONG ul = 0; ul < NUMBER_OF(StressManagers); ul++ )
      {
          CStressJobManager *pManager = StressManagers[ul];
  
          CSmallStringBuffer buffTestDirPath;
          ULONG ulThreads;
  
          if ((!buffTestDirPath.Win32Assign(BaseDirectory)) ||
              (!buffTestDirPath.Win32AppendPathElement(
              pManager->GetGroupName(),
              ::wcslen(pManager->GetGroupName()))))
              goto Exit;
              
          if ((!pManager->LoadFromDirectory(buffTestDirPath)) || 
              (!pManager->CreateWorkerThreads(&ulThreads)))
              goto Exit;
      }
  
      // wait for them all to get to their starts (should use a semaphore here)
      while (ThreadsWaiting != TotalThreads)
      {
          Sleep(0);
      }
  
      OutputDebugStringA("********************************\n");
      OutputDebugStringA("*                              *\n");
      OutputDebugStringA("*      start                   *\n");
      OutputDebugStringA("*                              *\n");
      OutputDebugStringA("********************************\n");
  
      // Go!
      if (!::SetEvent(ResumeThreadsEvent))
      {
          ::ReportFailure("SetEvent(ResumeThreadsEvent)\n");
          goto Exit;
      }
  
      //
      // Start the WFP stresser
      //
      for ( ULONG ul = 0; ul < NUMBER_OF(StressManagers); ul++ )
      {
          if (!StressManagers[ul]->StartJobs())
              goto Exit;
      }
  
      //
      // Let them run a while.
      //
      iRunTime = iRunTime * 60 * 1000;
      ::WaitForSingleObject(StopEvent, iRunTime);
  
      RequestShutdownMSIInstallTestThreads();
      RequestShutdownInstallThreads();
      RequestShutdownCreateActCtxThreads();
      RequestCsrssStressShutdown();
  
      for ( ULONG ul = 0; ul < NUMBER_OF(StressManagers); ul++ )
      {
          StressManagers[ul]->StopJobs();
      }
  
      ::Sleep(1000);
  
      WaitForMSIInstallTestThreads();
      WaitForInstallThreads();
      WaitForCreateActCtxThreads();
      WaitForCsrssStressShutdown();
  
      for ( ULONG ul = 0; ul < NUMBER_OF(StressManagers); ul++ )
      {
          StressManagers[ul]->WaitForAllJobsComplete();
      }
  
      iReturnStatus = EXIT_SUCCESS;
  Exit:
      CleanupMSIInstallTest();
      CleanupCreateActCtx();
      CleanupInstall();
      CleanupCsrssTests();
      for ( ULONG ul = 0; ul < NUMBER_OF(StressManagers); ul++ )
      {
          StressManagers[ul]->CleanupJobs();
      }
      Win32Cleanup();
      return iReturnStatus;
  }
  