/*++ Copyright (c) 1997 Microsoft Corporation Module Name: hwdatgen.c Abstract: This module creates a tool that generates hwcomp.dat and is designed for us by the NT build lab. It simply calls the code in hwcomp.lib, the same code that the Win9x upgrade uses to determine incompatibilities. Author: Jim Schmidt (jimschm) 12-Oct-1996 Revision History: --*/ #include "pch.h" #ifdef UNICODE #error UNICODE not allowed #endif #define MAX_SOURCE_DIRS 10 BOOL CancelFlag = FALSE; BOOL *g_CancelFlagPtr = &CancelFlag; #ifdef PRERELEASE BOOL g_Stress; #endif #ifdef DEBUG extern BOOL g_DoLog; #endif HANDLE g_hHeap; HINSTANCE g_hInst; CHAR g_TempDirBuf[MAX_MBCHAR_PATH]; // location for hwcomp.dat CHAR g_TempDirWackBuf[MAX_MBCHAR_PATH]; PSTR g_TempDir; PSTR g_TempDirWack; INT g_TempDirWackChars; PSTR g_WinDir; CHAR g_WinDirBuf[MAX_MBCHAR_PATH]; PCSTR g_SourceDirectories[MAX_SOURCE_COUNT]; // location of INFs DWORD g_SourceDirectoryCount; USEROPTIONS g_ConfigOptions; BOOL WINAPI MigUtil_Entry ( HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved ); VOID pInitProgBarVars ( VOID ); VOID HelpAndExit ( VOID ) { printf ("Command line syntax:\n\n" "hwdatgen [-i:] [-o:] [-c] [-v]\n\n" "Optional Arguments:\n" " -i: - Specifies input directory containing INF files.\n" " If -i is not specified, the default is %_NTTREE%\n" " -o: - Specifies path and file name of DAT file. By\n" " default, this file is %_NTTREE%\\hwcomp.dat\n" " -c - Clean build (deletes )\n" " -v - Verbose output\n" "\n" "A maximum of %u input directories can be specified.\n" "\n", MAX_SOURCE_DIRS ); exit(255); } INT __cdecl main ( INT argc, CHAR *argv[] ) { CHAR NtTree[MAX_MBCHAR_PATH]; CHAR InputPathBuf[MAX_SOURCE_DIRS][MAX_MBCHAR_PATH]; UINT SourceDirs = 0; CHAR OutputFileBuf[MAX_MBCHAR_PATH]; PSTR OutputFile; PSTR p; INT i; LONG rc; INT UIMode; BOOL CleanBuild; DWORD d; // for debugging only UINT u; DWORD Attribs; // // Get environment variables // p = getenv ("_NTx86TREE"); if (!p || !(*p)) { p = getenv ("_NTTREE"); } if (p && *p) { StringCopyA (NtTree, p); } else { StringCopyA (NtTree, "."); } // // Set defaults // g_TempDir = g_TempDirBuf; g_TempDirWack = g_TempDirWackBuf; g_WinDir = g_WinDirBuf; StringCopyA (OutputFileBuf, NtTree); AppendPathWack (OutputFileBuf); StringCatA (OutputFileBuf, "hwcomp.dat"); OutputFile = OutputFileBuf; StringCopyA (InputPathBuf[0], NtTree); UIMode = REGULAR_OUTPUT; CleanBuild = FALSE; ZeroMemory (&g_ConfigOptions, sizeof (g_ConfigOptions)); // // Parse command line // for (i = 1 ; i < argc ; i++) { if (argv[i][0] == '-' || argv[i][0] == '/') { switch (tolower (argv[i][1])) { case 'i': if (SourceDirs == MAX_SOURCE_DIRS) { HelpAndExit(); } if (argv[i][2] == ':') { StringCopyA (InputPathBuf[SourceDirs], &argv[i][3]); } else if (i + 1 < argc) { i++; StringCopyA (InputPathBuf[SourceDirs], argv[i]); } else { HelpAndExit(); } Attribs = GetFileAttributes (InputPathBuf[SourceDirs]); if (Attribs == INVALID_ATTRIBUTES || !(Attribs & FILE_ATTRIBUTE_DIRECTORY)) { HelpAndExit(); } SourceDirs++; break; case 'o': if (argv[i][2] == ':') { OutputFile = &argv[i][3]; } else if (i + 1 < argc) { i++; OutputFile = argv[i]; } else { HelpAndExit(); } break; case 'c': CleanBuild = TRUE; break; case 'v': UIMode = VERBOSE_OUTPUT; break; default: HelpAndExit(); } } else { HelpAndExit(); } } if (SourceDirs == 0) { SourceDirs = 1; } printf ("Building database of all NT-supported PNP IDs... Please wait.\n\n"); g_SourceDirectoryCount = SourceDirs; for (u = 0 ; u < SourceDirs ; u++) { g_SourceDirectories[u] = InputPathBuf[u]; if (!u) { printf ("Input path%s ", SourceDirs == 1 ? ": " : "s:"); } else { printf (" "); } printf ("%s\n", g_SourceDirectories[u]); } // // Init hwcomp.lib // pInitProgBarVars(); g_hHeap = GetProcessHeap(); g_hInst = GetModuleHandle (NULL); GetTempPathA (MAX_MBCHAR_PATH, g_TempDir); StringCopyA (g_TempDirWack, g_TempDir); AppendWack (g_TempDirWack); g_TempDirWackChars = CharCountA (g_TempDirWack); if (!GetWindowsDirectoryA (g_WinDir, MAX_MBCHAR_PATH)) { printf ("Memory allocation failure!\n"); return 254; } if (!MigUtil_Entry (g_hInst, DLL_PROCESS_ATTACH, NULL)) { printf ("Initialization error!\n"); return 254; } if (!HwComp_Entry (g_hInst, DLL_PROCESS_ATTACH, NULL)) { printf ("Initialization error!\n"); return 254; } #ifdef DEBUG g_DoLog = TRUE; #endif // // Build hwcomp.dat // if (CleanBuild) { SetFileAttributes (OutputFile, FILE_ATTRIBUTE_NORMAL); if (!DeleteFile (OutputFile)) { if (GetLastError() != ERROR_FILE_NOT_FOUND) { printf ("DeleteFile failed for %s. Win32 Error Code: %x\n", OutputFile, GetLastError ()); return 252; } } } if (!CreateNtHardwareList (g_SourceDirectories, g_SourceDirectoryCount, OutputFile, UIMode)) { rc = GetLastError(); printf ("Could not build complete device. Win32 Error Code: %x\n", rc); return 1; } else { printf ("%s was built successfully.\n", OutputFile); } // // Terminate hwcomp.lib // if (!HwComp_Entry (g_hInst, DLL_PROCESS_DETACH, NULL)) { printf ("Termination error!\n"); return 253; } if (!MigUtil_Entry (g_hInst, DLL_PROCESS_DETACH, NULL)) { printf ("Termination error!\n"); return 253; } return 0; } // // Stubs // HWND g_Component; HWND g_SubComponent; HANDLE g_ComponentCancelEvent; HANDLE g_SubComponentCancelEvent; VOID pInitProgBarVars ( VOID ) { g_Component = NULL; g_SubComponent = NULL; g_ComponentCancelEvent = CreateEvent (NULL, FALSE, FALSE, NULL); g_SubComponentCancelEvent = CreateEvent (NULL, FALSE, FALSE, NULL); } BOOL ProgressBar_SetWindowStringA ( IN HWND Window, IN HANDLE CancelEvent, IN PCSTR Message, OPTIONAL IN DWORD MessageId OPTIONAL ) { return TRUE; } BOOL TickProgressBar ( VOID ) { return TRUE; } BOOL TickProgressBarDelta ( IN UINT TickCount ) { return TRUE; } VOID InitializeProgressBar ( IN HWND ProgressBar, IN HWND Component, OPTIONAL IN HWND SubComponent, OPTIONAL IN BOOL *CancelFlagPtr OPTIONAL ) { return; } VOID TerminateProgressBar ( VOID ) { return; } VOID EndSliceProcessing ( VOID ) { return; } UINT RegisterProgressBarSlice ( IN UINT InitialEstimate ) { return 0; } VOID ReviseSliceEstimate ( IN UINT SliceId, IN UINT RevisedEstimate ) { return; } VOID BeginSliceProcessing ( IN UINT SliceId ) { }