Home | Info | Community | Development | myReactOS | Contact Us
ReactOS Development > Doxygenntvdm.c
Go to the documentation of this file.
00001 /* $Id: ntvdm.c 53284 2011-08-17 14:04:33Z akhaldi $ 00002 * 00003 * COPYRIGHT: See COPYING in the top level directory 00004 * PROJECT: ReactOS kernel 00005 * FILE: subsys/ntvdm/ntvdm->c 00006 * PURPOSE: Virtual DOS Machine 00007 * PROGRAMMER: Robert Dickenson (robd@mok.lvcm.com) 00008 * UPDATE HISTORY: 00009 * Created 23/10/2002 00010 */ 00011 00012 /* INCLUDES *****************************************************************/ 00013 #define WIN32_NO_STATUS 00014 #include <windows.h> 00015 #include <stdio.h> 00016 #include "resource.h" 00017 00018 #define NDEBUG 00019 #include <debug.h> 00020 00021 /* GLOBALS ******************************************************************/ 00022 00023 00024 /* FUNCTIONS *****************************************************************/ 00025 00026 void PrintString(char* fmt,...) 00027 { 00028 char buffer[512]; 00029 va_list ap; 00030 00031 va_start(ap, fmt); 00032 vsprintf(buffer, fmt, ap); 00033 va_end(ap); 00034 00035 OutputDebugStringA(buffer); 00036 } 00037 00038 /* 00039 GetVersion 00040 GetVolumeInformationW 00041 GetWindowsDirectoryA 00042 GlobalMemoryStatus 00043 HeapAlloc 00044 HeapCreate 00045 HeapDestroy 00046 HeapFree 00047 HeapReAlloc 00048 00049 GetNextVDMCommand 00050 ExitVDM 00051 RegisterConsoleVDM 00052 SetVDMCurrentDirectories 00053 VDMConsoleOperation 00054 WriteConsoleInputVDMW 00055 00056 NtSetLdtEntries 00057 NtTerminateProcess 00058 00059 NtMapViewOfSection 00060 NtUnmapViewOfSection 00061 00062 NtVdmControl 00063 */ 00064 typedef struct tag_VDM_CONFIG { 00065 int dos_options; 00066 int files; 00067 int buffers; 00068 WCHAR** device_list; 00069 //dos=high, umb 00070 //device=%SystemRoot%\system32\himem.sys 00071 //files=40 00072 } VDM_CONFIG, *PVDM_CONFIG; 00073 00074 typedef struct tag_VDM_AUTOEXEC { 00075 WCHAR** load_list; 00076 //lh %SystemRoot%\system32\mscdexnt.exe 00077 //lh %SystemRoot%\system32\redir 00078 //lh %SystemRoot%\system32\dosx 00079 } VDM_AUTOEXEC, *PVDM_AUTOEXEC; 00080 00081 typedef struct tag_VDM_CONTROL_BLOCK { 00082 HANDLE hHeap; 00083 PVOID ImageMem; 00084 VDM_CONFIG vdmConfig; 00085 VDM_AUTOEXEC vdmAutoexec; 00086 PROCESS_INFORMATION ProcessInformation; 00087 CHAR CommandLine[MAX_PATH]; 00088 CHAR CurrentDirectory[MAX_PATH]; 00089 00090 } VDM_CONTROL_BLOCK, *PVDM_CONTROL_BLOCK; 00091 00092 00093 BOOL 00094 StartVDM(PVDM_CONTROL_BLOCK vdm) 00095 { 00096 BOOL Result; 00097 STARTUPINFOA StartupInfo; 00098 00099 StartupInfo.cb = sizeof(StartupInfo); 00100 StartupInfo.lpReserved = NULL; 00101 StartupInfo.lpDesktop = NULL; 00102 StartupInfo.lpTitle = NULL; 00103 StartupInfo.dwFlags = 0; 00104 StartupInfo.cbReserved2 = 0; 00105 StartupInfo.lpReserved2 = 0; 00106 00107 Result = CreateProcessA(vdm->CommandLine, 00108 NULL, 00109 NULL, 00110 NULL, 00111 FALSE, 00112 DETACHED_PROCESS, 00113 NULL, 00114 NULL, 00115 &StartupInfo, 00116 &vdm->ProcessInformation); 00117 if (!Result) { 00118 PrintString("VDM: Failed to execute target process\n"); 00119 return FALSE; 00120 } 00121 WaitForSingleObject(vdm->ProcessInformation.hProcess, INFINITE); 00122 CloseHandle(vdm->ProcessInformation.hProcess); 00123 CloseHandle(vdm->ProcessInformation.hThread); 00124 return TRUE; 00125 } 00126 00127 BOOL 00128 ShutdownVDM(PVDM_CONTROL_BLOCK vdm) 00129 { 00130 BOOL result = TRUE; 00131 00132 return result; 00133 } 00134 00135 BOOL ReadConfigForVDM(PVDM_CONTROL_BLOCK vdm) 00136 { 00137 BOOL result = TRUE; 00138 DWORD dwError; 00139 HANDLE hFile; 00140 00141 hFile = CreateFileW(L"\\system32\\config.nt", 00142 GENERIC_READ, 00143 FILE_SHARE_READ, 00144 NULL, 00145 OPEN_ALWAYS /*OPEN_EXISTING*/, 00146 FILE_ATTRIBUTE_NORMAL, 00147 0); 00148 dwError = GetLastError(); 00149 if (hFile == INVALID_HANDLE_VALUE) { 00150 // error with file path or system problem? 00151 } else { 00152 if (dwError == 0L) { 00153 // we just created a new file, perhaps we should set/write some defaults? 00154 } 00155 if (dwError == ERROR_ALREADY_EXISTS) { 00156 // read the line entries and cache in some struct... 00157 } 00158 CloseHandle(hFile); 00159 } 00160 00161 hFile = CreateFileW(L"\\system32\\autoexec.nt", 00162 GENERIC_READ, 00163 FILE_SHARE_READ, 00164 NULL, 00165 OPEN_ALWAYS, 00166 FILE_ATTRIBUTE_NORMAL, 00167 0); 00168 dwError = GetLastError(); 00169 if (hFile == INVALID_HANDLE_VALUE) { 00170 // error with file path or system problem? 00171 } else { 00172 if (dwError == 0L) { 00173 // we just created a new file, perhaps we should set/write some defaults? 00174 } 00175 if (dwError == ERROR_ALREADY_EXISTS) { 00176 // read the line entries and cache in some struct... 00177 } 00178 CloseHandle(hFile); 00179 } 00180 00181 return result; 00182 } 00183 00184 BOOL 00185 LoadConfigDriversForVDM(PVDM_CONFIG vdmConfig) 00186 { 00187 BOOL result = TRUE; 00188 00189 return result; 00190 } 00191 00192 BOOL 00193 SetConfigOptionsForVDM(PVDM_AUTOEXEC vdmAutoexec) 00194 { 00195 BOOL result = TRUE; 00196 00197 return result; 00198 } 00199 00200 BOOL 00201 CreateVDM(PVDM_CONTROL_BLOCK vdm) 00202 { 00203 // BOOL result = TRUE; 00204 SYSTEM_INFO inf; 00205 MEMORYSTATUS stat; 00206 00207 00208 GlobalMemoryStatus(&stat); 00209 if (stat.dwLength != sizeof(MEMORYSTATUS)) { 00210 printf("WARNING: GlobalMemoryStatus() returned unknown structure version, size %ld, expected %d.\n", stat.dwLength, sizeof(stat)); 00211 } else { 00212 printf("Memory Load: %ld percent in use.\n", stat.dwMemoryLoad); 00213 printf("\t%ld total bytes physical memory.\n", stat.dwTotalPhys); 00214 printf("\t%ld available physical memory.\n", stat.dwAvailPhys); 00215 printf("\t%ld total bytes paging file.\n", stat.dwTotalPageFile); 00216 printf("\t%ld available paging file.\n", stat.dwAvailPageFile); 00217 printf("\t%lx total bytes virtual memory.\n", stat.dwTotalVirtual); 00218 printf("\t%lx available bytes virtual memory.\n", stat.dwAvailVirtual); 00219 00220 #define OUT_OF_HEADROOM 90 00221 if (stat.dwMemoryLoad > OUT_OF_HEADROOM) { 00222 DPRINT("VDM: system resources deemed to low to start VDM.\n"); 00223 //SetLastError(); 00224 return FALSE; 00225 } 00226 00227 } 00228 00229 GetSystemInfo(&inf); 00230 vdm->hHeap = HeapCreate(0, inf.dwAllocationGranularity, 0); 00231 if (vdm->hHeap == NULL) { 00232 DPRINT("VDM: failed to create heap.\n"); 00233 return FALSE; 00234 } 00235 00236 #define DEFAULT_VDM_IMAGE_SIZE 2000000 00237 vdm->ImageMem = HeapAlloc(vdm->hHeap, 0, DEFAULT_VDM_IMAGE_SIZE); 00238 if (vdm->ImageMem == NULL) { 00239 DPRINT("VDM: failed to allocate image memory from heap %x.\n", vdm->hHeap); 00240 HeapDestroy(vdm->hHeap); 00241 vdm->hHeap = NULL; 00242 return FALSE; 00243 } 00244 return TRUE; 00245 } 00246 00247 BOOL 00248 DestroyVDM(PVDM_CONTROL_BLOCK vdm) 00249 { 00250 BOOL result = TRUE; 00251 00252 if (vdm->ImageMem != NULL) { 00253 if (HeapFree(vdm->hHeap, 0, vdm->ImageMem) != FALSE) { 00254 DPRINT("VDM: failed to free memory from heap %x.\n", vdm->hHeap); 00255 result = FALSE; 00256 } 00257 vdm->ImageMem = NULL; 00258 } 00259 if (vdm->hHeap != NULL) { 00260 if (!HeapDestroy(vdm->hHeap)) { 00261 DPRINT("VDM: failed to destroy heap %x.\n", vdm->hHeap); 00262 result = FALSE; 00263 } 00264 vdm->hHeap = NULL; 00265 } 00266 return result; 00267 } 00268 00269 int WINAPI 00270 WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nShowCmd) 00271 { 00272 VDM_CONTROL_BLOCK VdmCB; 00273 DWORD Result; 00274 ULONG i; 00275 BOOL vdmStarted = FALSE; 00276 00277 WCHAR WelcomeMsg[RC_STRING_MAX_SIZE]; 00278 WCHAR PromptMsg[RC_STRING_MAX_SIZE]; 00279 CHAR InputBuffer[255]; 00280 00281 LoadStringW( GetModuleHandle(NULL), STRING_WelcomeMsg, WelcomeMsg,sizeof(WelcomeMsg) / sizeof(WelcomeMsg[0])); 00282 LoadStringW( GetModuleHandle(NULL), STRING_PromptMsg, PromptMsg ,sizeof(PromptMsg) / sizeof(PromptMsg[0])); 00283 00284 AllocConsole(); 00285 SetConsoleTitleW(L"ntvdm"); 00286 00287 WriteConsoleW(GetStdHandle(STD_OUTPUT_HANDLE), 00288 WelcomeMsg, lstrlenW(WelcomeMsg), // wcslen(WelcomeMsg), 00289 &Result, NULL); 00290 00291 if (!CreateVDM(&VdmCB)) { 00292 DPRINT("VDM: failed to create VDM.\n"); 00293 //SetLastError(); 00294 return 2; 00295 } 00296 00297 ReadConfigForVDM(&VdmCB); 00298 00299 if (!LoadConfigDriversForVDM(&(VdmCB.vdmConfig))) { 00300 DPRINT("VDM: failed to load configuration drivers.\n"); 00301 //SetLastError(); 00302 return 2; 00303 } 00304 if (!SetConfigOptionsForVDM(&(VdmCB.vdmAutoexec))) { 00305 DPRINT("VDM: failed to set configuration options.\n"); 00306 //SetLastError(); 00307 return 3; 00308 } 00309 00310 GetSystemDirectoryA(VdmCB.CommandLine, MAX_PATH); 00311 strcat(VdmCB.CommandLine, "\\hello.exe"); 00312 GetWindowsDirectoryA(VdmCB.CurrentDirectory, MAX_PATH); 00313 00314 for (;;) { 00315 WriteConsoleW(GetStdHandle(STD_OUTPUT_HANDLE), 00316 PromptMsg, lstrlenW(PromptMsg), // wcslen(PromptMsg), 00317 &Result, NULL); 00318 i = 0; 00319 do { 00320 ReadConsoleA(GetStdHandle(STD_INPUT_HANDLE), 00321 &InputBuffer[i], 1, 00322 &Result, NULL); 00323 if (++i >= (sizeof(InputBuffer) - 1)) { 00324 break; 00325 } 00326 } while (InputBuffer[i - 1] != '\n'); 00327 InputBuffer[i - 1] = '\0'; 00328 00329 if (InputBuffer[0] == 'r' || InputBuffer[0] == 'R') { 00330 if (!vdmStarted) { 00331 if (StartVDM(&VdmCB)) { 00332 vdmStarted = TRUE; 00333 } else { 00334 DPRINT("VDM: failed to start.\n"); 00335 } 00336 } else { 00337 DPRINT("VDM: already started.\n"); 00338 } 00339 } 00340 if (InputBuffer[0] == 's' || InputBuffer[0] == 'S') { 00341 if (vdmStarted) { 00342 if (ShutdownVDM(&VdmCB)) { 00343 vdmStarted = FALSE; 00344 } else { 00345 DPRINT("VDM: failed to shutdown.\n"); 00346 } 00347 } else { 00348 DPRINT("VDM: not started.\n"); 00349 } 00350 } 00351 if (InputBuffer[0] == 'q' || InputBuffer[0] == 'Q') { 00352 break; 00353 } 00354 } 00355 00356 if (!ShutdownVDM(&VdmCB)) { 00357 DPRINT("VDM: failed to cleanly shutdown VDM.\n"); 00358 //SetLastError(); 00359 return 5; 00360 } 00361 00362 if (!DestroyVDM(&VdmCB)) { 00363 DPRINT("VDM: failed to cleanly destroy VDM.\n"); 00364 //SetLastError(); 00365 return 6; 00366 } 00367 00368 ExitProcess(0); 00369 return 0; 00370 } Generated on Sun May 27 2012 04:37:41 for ReactOS by
1.7.6.1
|