Пример #1
0
void UnInitializeVirusList (VirusLnk *posVirusLnk)
{
	VirusLnk *posTemp = posVirusLnk;
	PAGED_CODE();

	while (posTemp != NULL)
	{
		//SMFree(posTemp->posGroupTbl);		
		posTemp = posVirusLnk->pNext;
		SMFree(posVirusLnk->osParam.pnParams);		
		SMFree(posVirusLnk);
		posVirusLnk = posTemp;
	}
}
Пример #2
0
void SetResolution(int width, int height)
{
  if ( !isCorrectVersion )
    return;

  // Resize game screen data buffer
  void *newBuf = SMAlloc(width * height);
  void *oldBuf = BW::BWDATA_GameScreenBuffer->data;
  SetBitmap(BW::BWDATA_GameScreenBuffer, width, height, newBuf);
  if ( oldBuf )
    SMFree(oldBuf);

  // Set new screen limits
  BW::BWDATA_ScreenLayers[5].width  = (WORD)width;
  BW::BWDATA_ScreenLayers[5].height = (WORD)height;
  SetRect(BW::BWDATA_ScrLimit, 0, 0, width - 1, height - 1);
  SetRect(BW::BWDATA_ScrSize,  0, 0, width,     height);

  // Resize game screen console (HUD) buffer
  newBuf = SMAlloc(width * height);
  oldBuf = BW::BWDATA_GameScreenConsole->data;
  SetBitmap(BW::BWDATA_GameScreenConsole, width, height, newBuf);
  if ( oldBuf )
    SMFree(oldBuf);

  // Recreate STrans thingy
  BW::BlizzVectorEntry<BW::TransVectorEntry> *transEntry = BW::BWDATA_TransMaskVector->begin;
  if ( (u32)transEntry && (u32)transEntry != (u32)&BW::BWDATA_TransMaskVector->begin )
  {
    HANDLE oldTrans = transEntry->container.hTrans;
    SetRect(&transEntry->container.info, 0, 0, width, height);
    STransCreateE(newBuf, width, height, 8, 0, 0, &transEntry->container.hTrans);
    if ( oldTrans )
      STransDelete(oldTrans);

    // call a function that does some weird stuff
    BW::BWFXN_UpdateBltMasks();
  }

  STransSetDirtyArrayInfo(width, height, 16, 16);

  // re-initialize w-mode or ddraw, this function can do both
  SetWMode(width, height, wmode);
}
Пример #3
0
  //------------------------------------------ GET MAP HASH --------------------------------------------------
  std::string Map::getMapHash()
  {
    unsigned char hash[20];
    char hexstring[42];
    std::string filename = Map::getPathName();

    // Open File
    HANDLE hFile = NULL;
    if ( !SFileOpenFileEx(NULL, filename.c_str(), SFILE_FROM_ABSOLUTE, &hFile) || !hFile)
    {
      char szPath[MAX_PATH];
      SStrCopy(szPath, filename.c_str(), MAX_PATH);
      SStrNCat(szPath, "\\staredit\\scenario.chk", MAX_PATH);
      if ( !SFileOpenFileEx(NULL, szPath, SFILE_FROM_MPQ, &hFile) || !hFile)
        return std::string("Error_map_cannot_be_opened");
    }

    // Obtain file size
    DWORD dwFileSize = SFileGetFileSize(hFile, 0);

    // Allocate memory
    void *pBuffer = SMAlloc(dwFileSize);
    if ( !pBuffer )
    {
      SFileCloseFile(hFile);
      return std::string("Error_could_not_allocate_memory");
    }

    // Read file
    DWORD dwBytesRead = 0;
    SFileReadFile(hFile, pBuffer, dwFileSize, &dwBytesRead, 0);

    // Calculate hash
    sha1::calc(pBuffer, dwBytesRead, hash);
    sha1::toHexString(hash, hexstring);

    // Free memory and return
    SMFree(pBuffer);
    SFileCloseFile(hFile);
    return string(hexstring);
  }
Пример #4
0
//--------------------------------------------- MEM ALLOC HOOK -----------------------------------------------
void *__stdcall _SMemAlloc(int amount, char *logfilename, int logline, char defaultValue)
{
  /* Call the original function */
  void *rval = nullptr;
  if ( _SMemAllocOld )
    rval = _SMemAllocOld(amount, logfilename, logline, defaultValue);
  else
    rval = SMemAlloc(amount, logfilename, logline, defaultValue);

  if ( isCorrectVersion )
  {
    if ( lastFile == "dlgs\\protoss.grp" || 
         lastFile == "dlgs\\terran.grp"  ||
         lastFile == "dlgs\\zerg.grp" )
    {
      if ( strcmpi(logfilename, ".?AU_DLGGRP@@") == 0 )
      {
        if ( leakUIClassLoc )
          SMFree(leakUIClassLoc);
        leakUIClassLoc = rval;
        BW::BWDATA_customList_UIDlgData[0] = BW::BWDATA_customList_UIDlgData;  // list with custom allocator?
        BW::BWDATA_customList_UIDlgData[1] = (void*)~(u32)BW::BWDATA_customList_UIDlgData;
      }
      else if ( strcmpi(logfilename, "Starcraft\\SWAR\\lang\\game.cpp") == 0 )
      {
        if ( leakUIGrpLoc )
          SMFree(leakUIGrpLoc);
        leakUIGrpLoc = rval;
        BW::BWDATA_customList_UIDlgData[0] = BW::BWDATA_customList_UIDlgData;  // list with custom allocator?
        BW::BWDATA_customList_UIDlgData[1] = (void*)~(u32)BW::BWDATA_customList_UIDlgData;
      }
    }
  } // isCorrectVer

  /* Save the allocated string table pointer */
  if ( lastFile == "rez\\stat_txt.tbl" )
  {
    BW::BWDATA_StringTableOff = (char*)rval;
    lastFile = "";
  }

  /* Save the allocated fog of war pointer */
  if ( amount == 0x40000 && strcmpi(logfilename, "Starcraft\\SWAR\\lang\\Gamemap.cpp") == 0 && logline == 606 )
  {
    BW::BWDATA_ActiveTileArray = (BW::activeTile*)rval;
  }

  /* Save the allocated mini-tile flags pointer */
  if ( lastFile.find(".vf4") != std::string::npos )
  {
    BW::BWDATA_MiniTileFlags = (BW::MiniTileMaps_type*)rval;
    lastFile = "";
  }

  /* Save the allocated SAI_Paths pointer */
  if ( strcmpi(logfilename, "Starcraft\\SWAR\\lang\\sai_PathCreate.cpp") == 0 && logline == 210 )
  {
    BW::BWDATA_SAIPathing = (BW::SAI_Paths*)rval;
  }

  /* Save the allocated tileset pointer */
  if ( lastFile.find(".cv5") != std::string::npos )
  {
    BW::BWDATA_TileSet    = (BW::TileType*)rval;
    lastFile = "";
  }

  /* Save the allocated map tile array pointer */
  if ( amount == 0x20000 && strcmpi(logfilename, "Starcraft\\SWAR\\lang\\Gamemap.cpp") == 0 && logline == 603 )
  {
    BW::BWDATA_MapTileArray = (u16*)rval;
  }

  return rval;
}
Пример #5
0
FunctionBinary* GetCleanFunction(UINT32 nStateConIndex)
{
	ULONG nSize;
	LARGE_INTEGER dnFuncOffset;
	FunctionBinary * posCleanReturnValue;
	PAGED_CODE();

	dnFuncOffset.QuadPart = GV.pocSMVirusDatFile->m_posCleanCondition_State[nStateConIndex].nFunctionOffset;
	posCleanReturnValue = (FunctionBinary *)SMAlloc(sizeof(FunctionBinary));
	if ( !posCleanReturnValue )
	{
		return NULL;
	}
	ZeroMemory(posCleanReturnValue, sizeof(FunctionBinary));

	if ( !NT_SUCCESS (CryptSeek(GV.pocSMVirusDatFile->m_posFile , &dnFuncOffset.QuadPart))) 
	{
		SMFree(posCleanReturnValue);
		return NULL; // Error Seeking File
	}

	nSize = sizeof(UINT32);
	if(!NT_SUCCESS(CryptRead(GV.pocSMVirusDatFile->m_posFile, &posCleanReturnValue->nLength, &nSize)))
	{
		SMFree(posCleanReturnValue);
		return NULL; // Error Reading File
	}
	
	nSize = sizeof(UINT8);
	if(!NT_SUCCESS(CryptRead(GV.pocSMVirusDatFile->m_posFile, &posCleanReturnValue->byIsChangeContext, &nSize)))
	{
		SMFree(posCleanReturnValue);
		return NULL; // Error Reading File
	}

	nSize = sizeof(UINT8);
	if(!NT_SUCCESS(CryptRead(GV.pocSMVirusDatFile->m_posFile, &posCleanReturnValue->byType, &nSize)))
	{
		SMFree(posCleanReturnValue);
		return NULL; // Error Reading File
	}

	posCleanReturnValue->pbyExp = (UINT8*)SMAlloc(sizeof(UINT8) * (posCleanReturnValue->nLength - (2 * sizeof(UINT8))));
	if( !posCleanReturnValue->pbyExp )
	{
		SMFree(posCleanReturnValue);
		return NULL; 
	}
	ZeroMemory(posCleanReturnValue->pbyExp, sizeof(UINT8) * (posCleanReturnValue->nLength - (2 * sizeof(UINT8))));

	nSize = (posCleanReturnValue->nLength - (2 * sizeof(UINT8)));
	
	if(!NT_SUCCESS(CryptRead(GV.pocSMVirusDatFile->m_posFile, posCleanReturnValue->pbyExp, &nSize)))
	{
		SMFree(posCleanReturnValue);
		return NULL; // Error Reading File
	}
	
	posCleanReturnValue->nLength = nSize;
	return posCleanReturnValue;
}
Пример #6
0
void UnLoadVMDatFile()
{
	UINT32 nIndex = 0;
	PAGED_CODE();

	if (GV.pocSMVirusDatFile->m_posVirusTable != NULL)	SMFree(GV.pocSMVirusDatFile->m_posVirusTable);
	if (GV.pocSMVirusDatFile->m_posStateTables != NULL)	SMFree(GV.pocSMVirusDatFile->m_posStateTables);
	if (GV.pocSMVirusDatFile->m_posFunctionBinaries != NULL)
	{
		for (; nIndex < GV.pocSMVirusDatFile->m_osHeader.nFunctionBinariesCount; nIndex++)
		{
			if (GV.pocSMVirusDatFile->m_posFunctionBinaries[nIndex].pbyExp != NULL)
			{
				SMFree(GV.pocSMVirusDatFile->m_posFunctionBinaries[nIndex].pbyExp);
			}
			else break;
		}
		SMFree(GV.pocSMVirusDatFile->m_posFunctionBinaries);
	}

	if (GV.pocSMVirusDatFile->m_posCondition_State != NULL)	SMFree(GV.pocSMVirusDatFile->m_posCondition_State);
	if (GV.pocSMVirusDatFile->m_posConditionExpression != NULL)
	{
		for (nIndex = 0; nIndex < GV.pocSMVirusDatFile->m_osHeader.nConditionIndexCount; nIndex++)
		{
			if (GV.pocSMVirusDatFile->m_posConditionExpression[nIndex].pbyExp != NULL)
			{
				SMFree(GV.pocSMVirusDatFile->m_posConditionExpression[nIndex].pbyExp);
			}
			else break;
		}
		SMFree(GV.pocSMVirusDatFile->m_posConditionExpression);
	}

	if (GV.pocSMVirusDatFile->m_posCleanVirusTable != NULL)	SMFree(GV.pocSMVirusDatFile->m_posCleanVirusTable);
	if (GV.pocSMVirusDatFile->m_pnVirusLength != NULL)	SMFree(GV.pocSMVirusDatFile->m_pnVirusLength);
	if (GV.pocSMVirusDatFile->m_posCleanStateTables != NULL)	SMFree(GV.pocSMVirusDatFile->m_posCleanStateTables);
	if (GV.pocSMVirusDatFile->m_posCleanCondition_State != NULL)	SMFree(GV.pocSMVirusDatFile->m_posCleanCondition_State);
	if (GV.pocSMVirusDatFile->m_posCleanConditionExpression != NULL)
	{
		for (nIndex = 0; nIndex < GV.pocSMVirusDatFile->m_osHeader.nCleanConditionIndexCount; nIndex++)
		{
			if (GV.pocSMVirusDatFile->m_posCleanConditionExpression[nIndex].pbyExp != NULL)
			{
				SMFree(GV.pocSMVirusDatFile->m_posCleanConditionExpression[nIndex].pbyExp);
			}
			else break;
		}
		SMFree(GV.pocSMVirusDatFile->m_posCleanConditionExpression);
	}
}
Пример #7
0
/* Deletes from |tree| and returns an item matching |item|.
   Returns a null pointer if no matching item found. */
void *
avl_delete (struct avl_table *tree, const void *item)
{
  /* Stack of nodes. */
  struct avl_node *pa[AVL_MAX_HEIGHT]; /* Nodes. */
  unsigned char da[AVL_MAX_HEIGHT];    /* |avl_link[]| indexes. */
  int k;                               /* Stack pointer. */

  struct avl_node *p;   /* Traverses tree to find node to delete. */
  int cmp;              /* Result of comparison between |item| and |p|. */

  //assert (tree != NULL && item != NULL);

  k = 0;
  p = (struct avl_node *) &tree->avl_root;
  for (cmp = -1; cmp != 0;
       cmp = /*tree->avl_compare */CompareMemory (item, p->avl_data, tree->avl_param))
    {
      int dir = cmp > 0;

      pa[k] = p;
      da[k++] = (unsigned char)dir;

      p = p->avl_link[dir];
      if (p == NULL)
        return NULL;
    }
  item = p->avl_data;

  if (p->avl_link[1] == NULL)
    pa[k - 1]->avl_link[da[k - 1]] = p->avl_link[0];
  else
    {
      struct avl_node *r = p->avl_link[1];
      if (r->avl_link[0] == NULL)
        {
          r->avl_link[0] = p->avl_link[0];
          r->avl_balance = p->avl_balance;
          pa[k - 1]->avl_link[da[k - 1]] = r;
          da[k] = 1;
          pa[k++] = r;
        }
      else
        {
          struct avl_node *s;
          int j = k++;

          for (;;)
            {
              da[k] = 0;
              pa[k++] = r;
              s = r->avl_link[0];
              if (s->avl_link[0] == NULL)
                break;

              r = s;
            }

          s->avl_link[0] = p->avl_link[0];
          r->avl_link[0] = s->avl_link[1];
          s->avl_link[1] = p->avl_link[1];
          s->avl_balance = p->avl_balance;

          pa[j - 1]->avl_link[da[j - 1]] = s;
          da[j] = 1;
          pa[j] = s;
        }
    }

  //tree->avl_alloc->libavl_free (/*tree->avl_alloc,*/ p);
  SMFree(p);

  //assert (k > 0);
  while (--k > 0)
    {
      struct avl_node *y = pa[k];

      if (da[k] == 0)
        {
          y->avl_balance++;
          if (y->avl_balance == +1)
            break;
          else if (y->avl_balance == +2)
            {
              struct avl_node *x = y->avl_link[1];
              if (x->avl_balance == -1)
                {
                  struct avl_node *w;
                  //assert (x->avl_balance == -1);
                  w = x->avl_link[0];
                  x->avl_link[0] = w->avl_link[1];
                  w->avl_link[1] = x;
                  y->avl_link[1] = w->avl_link[0];
                  w->avl_link[0] = y;
                  if (w->avl_balance == +1)
                    x->avl_balance = 0, y->avl_balance = -1;
                  else if (w->avl_balance == 0)
                    x->avl_balance = y->avl_balance = 0;
                  else /* |w->avl_balance == -1| */
                    x->avl_balance = +1, y->avl_balance = 0;
                  w->avl_balance = 0;
                  pa[k - 1]->avl_link[da[k - 1]] = w;
                }
              else
                {
                  y->avl_link[1] = x->avl_link[0];
                  x->avl_link[0] = y;
                  pa[k - 1]->avl_link[da[k - 1]] = x;
                  if (x->avl_balance == 0)
                    {
                      x->avl_balance = -1;
                      y->avl_balance = +1;
                      break;
                    }
                  else
                    x->avl_balance = y->avl_balance = 0;
                }
            }
        }
      else
        {
          y->avl_balance--;
          if (y->avl_balance == -1)
            break;
          else if (y->avl_balance == -2)
            {
              struct avl_node *x = y->avl_link[0];
              if (x->avl_balance == +1)
                {
                  struct avl_node *w;
                  //assert (x->avl_balance == +1);
                  w = x->avl_link[1];
                  x->avl_link[1] = w->avl_link[0];
                  w->avl_link[0] = x;
                  y->avl_link[0] = w->avl_link[1];
                  w->avl_link[1] = y;
                  if (w->avl_balance == -1)
                    x->avl_balance = 0, y->avl_balance = +1;
                  else if (w->avl_balance == 0)
                    x->avl_balance = y->avl_balance = 0;
                  else /* |w->avl_balance == +1| */
                    x->avl_balance = -1, y->avl_balance = 0;
                  w->avl_balance = 0;
                  pa[k - 1]->avl_link[da[k - 1]] = w;
                }
              else
                {
                  y->avl_link[0] = x->avl_link[1];
                  x->avl_link[1] = y;
                  pa[k - 1]->avl_link[da[k - 1]] = x;
                  if (x->avl_balance == 0)
                    {
                      x->avl_balance = +1;
                      y->avl_balance = -1;
                      break;
                    }
                  else
                    x->avl_balance = y->avl_balance = 0;
                }
            }
        }
    }

  tree->avl_count--;
  tree->avl_generation++;
  return (void *) item;
}
Пример #8
0
//------------------------------------------------- DLL MAIN -------------------------------------------------
BOOL APIENTRY DllMain(HMODULE, DWORD ul_reason_for_call, LPVOID)
{
  switch (ul_reason_for_call)
  {
    case DLL_PROCESS_ATTACH:
      {
#ifdef _DEBUG
        _CrtSetDbgFlag(_CRTDBG_ALLOC_MEM_DF | _CRTDBG_LEAK_CHECK_DF);
#endif
        // Retrieve the initial configuration stuff if not already
        InitPrimaryConfig();

        // Get revision/build automatically
        char szDllPath[MAX_PATH];

        DWORD dwDesiredRevision = 0;
        std::string aicfg = LoadConfigString("ai", BUILD_DEBUG ? "ai_dbg" : "ai", "_NULL");
        strncpy(szDllPath, aicfg.c_str(), MAX_PATH);

        if ( aicfg == "_NULL" )
        {
            BWAPIError("Could not find %s under ai in \"%s\" for revision identification.", BUILD_DEBUG ? "ai_dbg" : "ai", szConfigPath);
        }
        else
        {
          DWORD dwDesiredBuild    = 0; // 0 = undefined, 1 = release, 2 = debug

          // Tokenize and retrieve correct path for the instance number
          char *pszDll = strtok(szDllPath, ",");
          for ( unsigned int i = 0; i < gdwProcNum-1; ++i )
          {
            char *pszNext = strtok(NULL, ",");
            if ( !pszNext )
              break;
            pszDll = pszNext;
          }
          // Retrieve revision info if it exists
          char *pszLoadRevCheck = strchr(pszDll, ':');
          if ( pszLoadRevCheck )
          {
            pszLoadRevCheck[0] = 0;
            ++pszLoadRevCheck;
            sscanf(pszLoadRevCheck, "%u", &dwDesiredRevision);
          }

          // Remove spaces
          while ( isspace(pszDll[0]) )
            ++pszDll;

          // Open File
          HANDLE hFile = NULL;
          if ( !SFileOpenFileEx(NULL, pszDll, SFILE_FROM_ABSOLUTE, &hFile) || !hFile)
          {
              BWAPIError("Could not load module \"%s\" for revision identification.", pszDll);
          }
          else
          {
            // Obtain file size
            DWORD dwFileSize = SFileGetFileSize(hFile, 0);

            // Allocate memory
            char *pbBuffer = (char*)SMAlloc(dwFileSize);
            if ( !pbBuffer )
            {
                BWAPIError("Unable to allocate enough memory for module \"%s\" for revision identification.", pszDll);
            }
            else
            {
              // Read file
              DWORD dwBytesRead = 0;
              SFileReadFile(hFile, pbBuffer, dwFileSize, &dwBytesRead, 0);
              for ( u32 i = 0; i < dwBytesRead && (dwDesiredRevision == 0 || dwDesiredBuild == 0); ++i )
              {
                if ( dwDesiredRevision == 0 && memcmp(&pbBuffer[i], "XBWAPIXREVISIONXSTAMPX", 22) == 0 )
                {
                  i += 22;
                  sscanf(&pbBuffer[i], "%u", &dwDesiredRevision);
                  i += 5;
                }  // if REVISION
                if ( memcmp(&pbBuffer[i], "XBWAPIXBUILDXSTAMPX", 19) == 0 )
                {
                  i += 19;
                  if ( strcmp(&pbBuffer[i], "DEBUG") == 0 )
                  {
                    dwDesiredBuild = 2;
                    i += 6;
                  }
                  else if ( strcmp(&pbBuffer[i], "RELEASE") == 0 )
                  {
                    dwDesiredBuild = 1;
                    i += 8;
                  }
                } // if BUILD
              } // for (iterate file)
              // Free memory and close file
              SMFree(pbBuffer);
              SFileCloseFile(hFile);
            } // buffer was allocated
          } // file was opened

          /* Do revision checking */
          if ( dwDesiredRevision > 0 && dwDesiredRevision != SVN_REV )
          {
            // revision that ai_dll_# for multiple instances was introduced
            if ( gdwProcNum && dwDesiredRevision < 2753 && showWarn )
            {
              char err[512];
              sprintf(err, "Revision %u is not compatible with multiple instances.\nExpecting revision 2753 (BWAPI Beta 3.1) or greater. If you proceed, the older revision of BWAPI will attempt to load its module from ai_dll instead of the multi-instance specification. Do you want to continue anyway?", dwDesiredRevision);
              BWAPIError("%s", err);
              if ( MessageBox(NULL, err, "Error", MB_YESNO | MB_ICONWARNING | MB_DEFBUTTON1 | MB_TASKMODAL) == IDNO )
                return TRUE;
            } // revision is old

            if ( dwDesiredBuild == 0 )
              dwDesiredBuild = BUILD_DEBUG + 1;
            char szRevModule[MAX_PATH];
            sprintf_s(szRevModule, MAX_PATH, "%sbwapi-data\\revisions\\%u%s.dll", szInstallPath, dwDesiredRevision, dwDesiredBuild == 2 ? "d" : "");
            HMODULE hLib = LoadLibrary(szRevModule);
            if ( hLib )
            {
              if ( showWarn )
              {
                char msg[MAX_PATH+32];
                char szLoadedName[MAX_PATH];
                GetModuleFileName(hLib, szLoadedName, MAX_PATH);
                sprintf_s(msg, MAX_PATH+32, "Loaded \"%s\" instead.", szLoadedName);
                MessageBox(NULL, msg, "Success", MB_OK | MB_ICONINFO);
              }
              return TRUE;
            }

            if ( showWarn )
            {
              char err[512];
              sprintf(err, "Couldn't find revision module \"%s\" of which the AI DLL was compiled for. Do you want to try using the current revision instead?", szRevModule);
              BWAPIError("%s", err);
              if ( MessageBox(NULL, err, "Error", MB_YESNO | MB_ICONWARNING | MB_DEFBUTTON1 | MB_TASKMODAL) == IDNO )
                return TRUE;
            }
          } // specified rev is not this one
          else if ( dwDesiredBuild && BUILD_DEBUG + 1 != dwDesiredBuild )
          {
            char envBuffer[MAX_PATH];
            if ( !GetEnvironmentVariable("ChaosDir", envBuffer, MAX_PATH) )
              if ( !GetCurrentDirectory(MAX_PATH, envBuffer) && showWarn )
                BWAPIError("Could not find ChaosDir or current directory for build identification.");

            SStrNCat(envBuffer, "\\BWAPI", MAX_PATH);
            if ( dwDesiredBuild == 2 )
              SStrNCat(envBuffer, "d", MAX_PATH);
            SStrNCat(envBuffer, ".dll", MAX_PATH);

            HMODULE hLib = LoadLibrary(envBuffer);
            if ( hLib )
            {
              if ( showWarn )
              {
                char msg[MAX_PATH+32];
                sprintf_s(msg, MAX_PATH+32, "Loaded \"%s\" instead.", envBuffer);
                MessageBox(NULL, msg, "Success", MB_OK | MB_ICONINFO);
              }
              return TRUE;
            }

            if ( showWarn )
            {
              char err[512];
              sprintf(err, "Couldn't find build module \"%s\" of which the AI DLL was compiled for. Do you want to try using the current build instead?", envBuffer);
              BWAPIError("%s", err);
              if ( MessageBox(NULL, err, "Error", MB_YESNO | MB_ICONWARNING | MB_DEFBUTTON1 | MB_TASKMODAL) == IDNO )
                return TRUE;
            }
            return TRUE;
          }
        } // module str was found

        // Do version checking
        CheckVersion();

        // Load the auto-menu config
        BWAPI::BroodwarImpl.loadAutoMenuData();

        // Apply all hacks and patches to the game
        ApplyCodePatches();

        // Initialize BWAPI
        BWAPI::BWAPI_init();

        // Create our thread that persistently applies hacks
        CreateThread(NULL, 0, &PersistentPatch, NULL, 0, NULL);

        return TRUE;
      }
  }
  return TRUE;
}