📄 bootstrapper_util.cpp
字号:
//////////////////////////////////////////////////////////////////////////////** * GetFileVersionNumber * */DWORD GetFileVersionNumber(LPSTR szFilename, DWORD * pdwMSVer, DWORD * pdwLSVer){ DWORD dwResult = NOERROR; unsigned uiSize; DWORD dwVerInfoSize; DWORD dwHandle; BYTE *prgbVersionInfo = NULL; VS_FIXEDFILEINFO *lpVSFixedFileInfo = NULL; DWORD dwMSVer = 0xffffffff; DWORD dwLSVer = 0xffffffff; dwVerInfoSize = GetFileVersionInfoSize(szFilename, &dwHandle); if (0 != dwVerInfoSize) { prgbVersionInfo = (LPBYTE) GlobalAlloc(GPTR, dwVerInfoSize); if (NULL == prgbVersionInfo) { dwResult = ERROR_NOT_ENOUGH_MEMORY; goto Finish; } // Read version stamping info if (GetFileVersionInfo(szFilename, dwHandle, dwVerInfoSize, \ prgbVersionInfo)) { // get the value for Translation if (VerQueryValue(prgbVersionInfo, "\\", \ (LPVOID*)&lpVSFixedFileInfo, &uiSize) \ && (uiSize != 0)) { dwMSVer = lpVSFixedFileInfo->dwFileVersionMS; dwLSVer = lpVSFixedFileInfo->dwFileVersionLS; } } else { dwResult = GetLastError(); goto Finish; } } else { dwResult = GetLastError(); }Finish: if (NULL != prgbVersionInfo) GlobalFree(prgbVersionInfo); if (pdwMSVer) *pdwMSVer = dwMSVer; if (pdwLSVer) *pdwLSVer = dwLSVer; return dwResult;}////////////////////////////////////////////////////////////////////////////////////////////////////** * Extract the specified resources (The MSI file) from the executable file * */void ExtractMsiFromResource(TCHAR* msiFileName){ HRSRC hResource = FindResource(NULL, MAKEINTRESOURCE(RES_ID_MSI), \ RT_RCDATA); HGLOBAL hResourceLoaded; LPBYTE lpBuffer; if (NULL != hResource) { hResourceLoaded = LoadResource(NULL, hResource); if (NULL != hResourceLoaded) { lpBuffer = (LPBYTE) LockResource(hResourceLoaded); if (NULL != lpBuffer) { //Get the file size DWORD dwFileSize = SizeofResource(NULL, hResource); //create the MSI file HANDLE hMsiFile = CreateFile(msiFileName, GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL); DWORD dwBytesWritten = 0; if (INVALID_HANDLE_VALUE != hMsiFile) { //Copy data into the file WriteFile(hMsiFile, lpBuffer, dwFileSize, \ &dwBytesWritten, NULL); CloseHandle(hMsiFile); } } } }}////////////////////////////////////////////////////////////////////////////////////////////** * Extract the UUID info from resource */void ExtractUUIDFromResource(LPTSTR uuid){ HRSRC hResource = FindResource(NULL, MAKEINTRESOURCE(BLOCK_ID_UUID), \ RT_STRING); if (NULL != hResource) { LoadString(NULL, RES_ID_UUID, uuid, 256); }}///////////////////////////////////////////////////////////////////////////////////////////** * Extract the localization flag from resource */bool IsLocalizationSupported(){ TCHAR localizationFlag[80]; //Extract the localization flag from resource HRSRC hResource = FindResource(NULL, MAKEINTRESOURCE(BLOCK_ID_FLAG), \ RT_STRING); if (NULL != hResource) { LoadString(NULL, RES_ID_LOCALIZATION_FLAG, localizationFlag, 256); } if (0 == strcmp(localizationFlag, "localization supported") ) { return true; } else { return false; }}////////////////////////////////////////////////////////////////////////////////** * Create the temporary file path, the extracted msi file will be placed there * * @param pTempDir Pointer to the string of the temprary directory name */void CreateTempDir(TCHAR* pTempDir){ //BASE_PATH: Get the system temporary path TCHAR BASE_PATH[MAX_PATH_SIZE] = "\0"; DWORD dwLenInstallerPath = MAX_PATH_SIZE; GetTempPath(dwLenInstallerPath, (LPTSTR)BASE_PATH); //Generate a unique temporary directory GetTempDirName(BASE_PATH, pTempDir); CreateDirectory(pTempDir, NULL);}/////////////////////////////////////////////////////////////////////////////** * Generate a unique tempory directory name * * @param baseDir Specify the base directory (in) * @param tempDir String buffer containing the generated dir name (in, out) * * @return 1 if succeed */int GetTempDirName(TCHAR* pBaseDir, TCHAR* pTempDir){ TCHAR dirPrefix[] = "javaws"; if (0 != GetTempFileName(pBaseDir, dirPrefix, 0, pTempDir)) { DeleteFile(pTempDir); return 1; } return 0;}////////////////////////////////////////////////////////////////////////////////** * Get the temporary msi file name */void GetMsiFileName(TCHAR * msiFileDir, TCHAR* msiFileName){ StringCchCopy(msiFileName, MAX_PATH_SIZE, msiFileDir); StringCchCat(msiFileName, MAX_PATH_SIZE, "\\install.msi");}///////////////////////////////////////////////////////////////////////////////** * Recursively remove the specified directory and all its files and sub-dirs. * * @param dirName Specify the directory name * @return 1 if succeed */int RemoveDir(TCHAR * dirName){ WIN32_FIND_DATA fileData; HANDLE hSearch; TCHAR filePattern[MAX_PATH_SIZE] = {0}; StringCchPrintf(filePattern, MAX_PATH_SIZE, "%s\\%s", dirName, "*"); BOOL fFinished = false; hSearch = FindFirstFile(filePattern, &fileData); while (!fFinished) { if (fileData.dwFileAttributes == FILE_ATTRIBUTE_DIRECTORY) { if ((strcmp(fileData.cFileName, ".") != 0) \ && (strcmp(fileData.cFileName, "..") != 0)) { //For none "." & ".." directory, take resursive //handling mechanism TCHAR nextDirName[MAX_PATH_SIZE] = {0}; StringCchPrintf(nextDirName, MAX_PATH_SIZE, "%s\\%s", dirName, \ fileData.cFileName); RemoveDir(nextDirName); } } else { //For general file, just delete TCHAR fullFileName[MAX_PATH_SIZE] = {0}; StringCchPrintf(fullFileName, MAX_PATH_SIZE, "%s\\%s", dirName, \ fileData.cFileName); DeleteFile(fullFileName); } if (!FindNextFile(hSearch, &fileData) && (GetLastError() == \ ERROR_NO_MORE_FILES)) fFinished = true; } //Close the search handle FindClose(hSearch); //Then delete the directory RemoveDirectory(dirName); return 1;}///////////////////////////////////////////////////////////////////////////////** * Modify the relevant field in the MSI file * They are Codepage & Template of Table Summary Info */void UpdateMsiSummaryInfo(LPCTSTR msiFileName, UINT codePage, WORD langID){ if (!IsLocalizationSupported()) { //No localization support, no changes to the MSI file return; } int errorCode; MSIHANDLE msiDatabase, msiSummaryInfo; errorCode = MsiOpenDatabase(msiFileName, MSIDBOPEN_TRANSACT, &msiDatabase); if (ERROR_SUCCESS == errorCode) //Database open successfully { errorCode = MsiGetSummaryInformation(msiDatabase, 0, 5, \ &msiSummaryInfo); //Open summary Info successfully if (ERROR_SUCCESS == errorCode) { int errorCode1, errorCode2; //Update codepage field errorCode1 = MsiSummaryInfoSetProperty(msiSummaryInfo, 1, VT_I2, \ codePage, NULL, NULL); //Get the string for the template, which is ";"+langID TCHAR strTemplate[80] = "\0"; StringCchPrintf(strTemplate, 80, ";%d", langID); //Update template field errorCode2 = MsiSummaryInfoSetProperty(msiSummaryInfo, 7, \ VT_LPSTR, 0, NULL, \ strTemplate); if ((ERROR_SUCCESS == errorCode1) && (ERROR_SUCCESS == errorCode2)) { MsiSummaryInfoPersist(msiSummaryInfo); MsiDatabaseCommit(msiDatabase); } MsiCloseHandle(msiSummaryInfo); } MsiCloseHandle(msiDatabase); }}///////////////////////////////////////////////////////////////////////////////////////////////** * Get JavaWS home directory */unsigned int GetJavawsHome(){ TCHAR KEY_JAVAWS[] = "SOFTWARE\\JavaSoft\\Java Web Start"; TCHAR KEY_JAVAWS_CURRENT_VERSION[1024] = {0}; TCHAR VALUE_JAVAWS_CURRNET_VERSION[] = "CurrentVersion"; TCHAR VALUE_JAVAWS_HOME[] = "Home"; TCHAR JAVAWS_VERSION[128] = {0}; HKEY hKey; DWORD dwType; DWORD cbData; //Open the key HKEY_LOCAL_MACHINE\\SOFTWAER\JavaSoft\\Java Web Start if (RegOpenKeyEx(HKEY_LOCAL_MACHINE, KEY_JAVAWS, 0, KEY_READ, &hKey) \ == ERROR_SUCCESS) { cbData = 128; //Get the value of CurrentVersion if (RegQueryValueEx(hKey, (LPCTSTR)VALUE_JAVAWS_CURRNET_VERSION, NULL, \ &dwType, (LPBYTE)&JAVAWS_VERSION, &cbData) \ == ERROR_SUCCESS) { RegCloseKey(hKey);#ifdef _DEBUG printf("[Info]Java WS current version is %s\n", JAVAWS_VERSION);#endif if (strncmp(JAVAWS_VERSION, MINIMUM_JAVAWS_VERSION, 128) < 0) { //JavaWS version Less then 1.5.0, does not meet the // minimum reqiurement return ERROR_JAVAWS_VERSION_ERROR; } return 0; } } return ERROR_MSI_DB_ERROR;}////////////////////////////////////////////////////////////////////////////////** * Execute MSIexec to install the msi file */int LaunchMsi(LPCTSTR msiFileName, TCHAR* pStrLocalName){ // install the jnlp software STARTUPINFO stinfo = {0}; //info of the window stinfo.cb = sizeof(STARTUPINFO); PROCESS_INFORMATION procinfo; //info of the process TCHAR CREATEPROCESS[200] = {0}; if (0 != strcmp(pStrLocalName, "en")) { //None English local, need to apply transform TCHAR sysMsiTransform[80]; TCHAR custMsiTransform[80]; //System Transform naming schema is sys_localname, e.g. sys_zh_CN StringCchPrintf(sysMsiTransform, 80, ":sys_%s", pStrLocalName); //Customized Transform naming schema is cust_localname, e.g. cust_zh_cn StringCchPrintf(custMsiTransform, 80, ":cust_%s", pStrLocalName); if (IsLocalizationSupported()) { //Localization supported StringCchPrintf(CREATEPROCESS, 200, "msiexec /i %s TRANSFORMS=%s", \ msiFileName, custMsiTransform); } else { //No localization support StringCchPrintf(CREATEPROCESS, 200, "msiexec /i %s", msiFileName); } } else { //English locale, no transform is need StringCchPrintf(CREATEPROCESS, 200, "msiexec /i %s", msiFileName); }#ifdef _DEBUG printf("[Info] Will now launch msi installation command: %s...\n", \ CREATEPROCESS);#endif //Create the process if(!CreateProcess(NULL, CREATEPROCESS, NULL, NULL, FALSE, \ CREATE_NO_WINDOW, NULL, NULL, &stinfo, &procinfo)) { return -1; } // wait for the end of the process WaitForSingleObject(procinfo.hProcess, INFINITE);#ifdef _DEBUG TCHAR strInfo[MAX_INFO_SIZE] = "\0"; StringCchPrintf( \ strInfo, MAX_INFO_SIZE, "%s%s \n", "[Info] The software has been successfully installed/uninstalled. ", "Thank you for using this software and Have a good day!"); printf(strInfo);#endif CloseHandle(procinfo.hProcess); CloseHandle(procinfo.hThread); return 0;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -