int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow) { int nReturnVal; // Stage 1: Figure out the situation with the installation of .NET if (IsNetfx20Installed()) { // .NET's already installed, our job is done! nReturnVal = 0; } else { const TCHAR* szNetfxInstallerFileName; const TCHAR* szNetfxDownloadUrl; WORD wCpu = GetProcessorArchitecture(); switch (wCpu) { case PROCESSOR_ARCHITECTURE_INTEL: szNetfxInstallerFileName = g_szNetfx20x86InstallerFileName; szNetfxDownloadUrl = g_szNetfx20x86DownloadUrl; break; case PROCESSOR_ARCHITECTURE_AMD64: szNetfxInstallerFileName = g_szNetfx20x64InstallerFileName; szNetfxDownloadUrl = g_szNetfx20x64DownloadUrl; break; default: szNetfxInstallerFileName = NULL; szNetfxDownloadUrl = g_szNetfx20DispatchDownloadUrl; break; } // .NET 2.0 is not installed. But if we have the installer in front of us, // then try to install it! if (NULL != szNetfxInstallerFileName && FileExists(szNetfxInstallerFileName)) { // First, tell the user what we're about to do. MessageBox(NULL, g_szNetfx20FoundText, g_szMessageBoxTitle, MB_OK | MB_ICONINFORMATION); // .NET installer is present, so let's try and install it DWORD dwResult = OurShellExecute(szNetfxInstallerFileName, NULL, true); switch (dwResult) { // Success case 0: nReturnVal = 0; break; // Reboot required case 8192: MessageBox(NULL, g_szNetfxInstallRebootRequired, g_szMessageBoxTitle, MB_OK | MB_ICONINFORMATION); nReturnVal = 1; break; // They cancelled. No sense in putting up another error message. case 1602: nReturnVal = 1; break; // Other. Interpreted as failure. default: { TCHAR szErrorText[1024]; HRESULT hr = StringCchPrintf( szErrorText, sizeof(szErrorText) / sizeof(szErrorText[0]), g_szNetfxInstallFailureTextFormat, dwResult, dwResult); if (SUCCEEDED(hr)) { MessageBox(NULL, szErrorText, g_szMessageBoxTitle, MB_OK | MB_ICONERROR); } } nReturnVal = 1; break; } } else { // .NET not installed, and the installer isn't around. Ask them to go to a website in order to install it. int nResult = MessageBox(NULL, g_szNetfx20NotFoundText, g_szMessageBoxTitle, MB_OKCANCEL | MB_ICONERROR); if (IDOK == nResult) { OurShellExecute(szNetfxDownloadUrl, NULL, false); } nReturnVal = 1; } } // Stage 2: Launch our setup app! if (0 == nReturnVal) { OurShellExecute(g_szPdnInstallerFileName, GetCommandLine(), true); } return nReturnVal; }
void FCrashInfo::GenerateReport( const FString& DiagnosticsPath ) { FArchive* ReportFile = IFileManager::Get().CreateFileWriter( *DiagnosticsPath ); if( ReportFile != NULL ) { FString Line; WriteLine( ReportFile, TCHAR_TO_UTF8( TEXT( "Generating report for minidump" ) ) ); WriteLine( ReportFile ); if ( EngineVersion.Len() > 0 ) { Line = FString::Printf( TEXT( "Application version %s" ), *EngineVersion ); WriteLine( ReportFile, TCHAR_TO_UTF8( *Line ) ); } else if( Modules.Num() > 0 ) { Line = FString::Printf( TEXT( "Application version %d.%d.%d" ), Modules[0].Major, Modules[0].Minor, Modules[0].Patch ); WriteLine( ReportFile, TCHAR_TO_UTF8( *Line ) ); } Line = FString::Printf( TEXT( " ... built from changelist %d" ), BuiltFromCL ); WriteLine( ReportFile, TCHAR_TO_UTF8( *Line ) ); if( LabelName.Len() > 0 ) { Line = FString::Printf( TEXT( " ... based on label %s" ), *LabelName ); WriteLine( ReportFile, TCHAR_TO_UTF8( *Line ) ); } WriteLine( ReportFile ); Line = FString::Printf( TEXT( "OS version %d.%d.%d.%d" ), SystemInfo.OSMajor, SystemInfo.OSMinor, SystemInfo.OSBuild, SystemInfo.OSRevision ); WriteLine( ReportFile, TCHAR_TO_UTF8( *Line ) ); Line = FString::Printf( TEXT( "Running %d %s processors" ), SystemInfo.ProcessorCount, GetProcessorArchitecture( SystemInfo.ProcessorArchitecture ) ); WriteLine( ReportFile, TCHAR_TO_UTF8( *Line ) ); Line = FString::Printf( TEXT( "Exception was \"%s\"" ), *Exception.ExceptionString ); WriteLine( ReportFile, TCHAR_TO_UTF8( *Line ) ); WriteLine( ReportFile ); Line = FString::Printf( TEXT( "Source context from \"%s\"" ), *SourceFile ); WriteLine( ReportFile, TCHAR_TO_UTF8( *Line ) ); WriteLine( ReportFile ); Line = FString::Printf( TEXT( "<SOURCE START>" ) ); WriteLine( ReportFile, TCHAR_TO_UTF8( *Line ) ); for( int32 LineIndex = 0; LineIndex < SourceContext.Num(); LineIndex++ ) { Line = FString::Printf( TEXT( "%s" ), *SourceContext[LineIndex] ); WriteLine( ReportFile, TCHAR_TO_UTF8( *Line ) ); } Line = FString::Printf( TEXT( "<SOURCE END>" ) ); WriteLine( ReportFile, TCHAR_TO_UTF8( *Line ) ); WriteLine( ReportFile ); Line = FString::Printf( TEXT( "<CALLSTACK START>" ) ); WriteLine( ReportFile, TCHAR_TO_UTF8( *Line ) ); for( int32 StackIndex = 0; StackIndex < Exception.CallStackString.Num(); StackIndex++ ) { Line = FString::Printf( TEXT( "%s" ), *Exception.CallStackString[StackIndex] ); WriteLine( ReportFile, TCHAR_TO_UTF8( *Line ) ); } Line = FString::Printf( TEXT( "<CALLSTACK END>" ) ); WriteLine( ReportFile, TCHAR_TO_UTF8( *Line ) ); WriteLine( ReportFile ); Line = FString::Printf( TEXT( "%d loaded modules" ), Modules.Num() ); WriteLine( ReportFile, TCHAR_TO_UTF8( *Line ) ); for( int32 ModuleIndex = 0; ModuleIndex < Modules.Num(); ModuleIndex++ ) { FCrashModuleInfo& Module = Modules[ModuleIndex]; FString ModuleDirectory = FPaths::GetPath(Module.Name); FString ModuleName = FPaths::GetBaseFilename( Module.Name, true ) + FPaths::GetExtension( Module.Name, true ); FString ModuleDetail = FString::Printf( TEXT( "%40s" ), *ModuleName ); FString Version = FString::Printf( TEXT( " (%d.%d.%d.%d)" ), Module.Major, Module.Minor, Module.Patch, Module.Revision ); ModuleDetail += FString::Printf( TEXT( " %22s" ), *Version ); ModuleDetail += FString::Printf( TEXT( " 0x%016x 0x%08x" ), Module.BaseOfImage, Module.SizeOfImage ); ModuleDetail += FString::Printf( TEXT( " %s" ), *ModuleDirectory ); WriteLine( ReportFile, TCHAR_TO_UTF8( *ModuleDetail ) ); } WriteLine( ReportFile ); // Write out the processor debugging log WriteLine( ReportFile, TCHAR_TO_UTF8( *Report ) ); Line = FString::Printf( TEXT( "Report end!" ) ); WriteLine( ReportFile, TCHAR_TO_UTF8( *Line ) ); ReportFile->Close(); delete ReportFile; } }