从Entry Point到main函数调用(二):GetVersion
之前(1)篇中大致介绍了mainCRTStartup,但是其中一些调用到的函数并未深究,现打算逐一剖析它们。
GetVersion
GetVersion函数是kernel32.dll中提供的API,用于获取当前Win平台的版本。准确的说,GetVersion可以获得3个信息:
1. OSPlatformId
2. OSBuildNumber
3. OSMinorVersion
4. OSMajorVersion
其中比较诡异的是OSPlatformId,在GetVersion的过程当中它被获得过,但是返回的时候又没了...所以只剩下2、3、4
可以用OD来跟进GetVersion:
mov eax, dword ptr fs:[18] mov ecx, dword ptr [eax+30] mov eax, dword ptr [ecx+B0] // 获取 OSPlatformId movzx edx, word ptr [ecx+AC] // 获取 OSBuildNumber xor eax, FFFFFFFE shl eax, 0E // 几次左移,把OSPlatformId的信息给移没了... or eax, edx shl eax, 8 or eax, dword ptr [ecx+A8] // 获取 OSMinorVersion shl eax, 8 or eax, dword ptr [ecx+A4] // 获取 OSMajorVersion retn
GetVersion主要是去PEB(Process Environment Block)结构中访问当前的OS信息,每个进程都会有自己独立的PEB。想要获取当前进程的PEB地址,首先要先访问TEB(Thread Environment Block )结构。因为TEB结构的30偏移量处中存放了PEB结构的指针。FS 寄存器指向了当前活动线程的TEB结构,其中偏移位置18表示了FS 段寄存器在内存中的镜像地址。
004 线程堆栈顶部
008 线程堆栈底部
00C SubSystemTib
010 FiberData
014 ArbitraryUserPointer
018 FS段寄存器在内存中的镜像地址
020 进程PID
024 线程ID
02C 指向线程局部存储指针
030 PEB结构地址(进程结构)
034 上个错误号
因此
mov eax, dword ptr fs:[18]
mov ecx, dword ptr [eax+30]
两句表示根据TEB获取PEB的指针,并且存放在ECX中。拿到PEB的指针后,就可以去PEB中拿OS的信息。
PEB结构中关于OS信息的偏移量如下:
……
/*0A4*/ ULONG OSMajorVersion;
/*0A8*/ ULONG OSMinorVersion;
/*0AC*/ USHORT OSBuildNumber;
/*0AE*/ USHORT OSCSDVersion;
/*0B0*/ ULONG OSPlatformId;
……
如果是XP用户,那么GetVersion最终的返回值应该是:0A280105 。
其中 0A28表示XP build版本是2600,01表示OSMinorVersion,05表示OSMajorVersion 。
中间被忽略掉的 OSPlatformId 信息可以为:
-
VER_PLATFORM_WIN32s 或 0x0000,用于指定 Microsoft Windows 3.1。
-
VER_PLATFORM_WIN32_WINDOWS 或 0x0001,用于指定 Windows 95、Windows 98 或从其继承的操作系统。
-
VER_PLATFORM_WIN32_NT 或 0x0010,用于指定 Windows NT 或从其继承的操作系统。
另外,还有一些补充的OS信息如下:
(摘录自 http://msdn.microsoft.com/zh-cn/library/ms724833%28v=VS.85%29.aspx )
Operating system | Version number | dwMajorVersion | dwMinorVersion |
Windows 7 | 6.1 | 6 | 1 |
Windows Server 2008 R2 | 6.1 | 6 | 1 |
Windows Server 2008 | 6.0 | 6 | 0 |
Windows Vista | 6.0 | 6 | 0 |
Windows Server 2003 R2 | 5.2 | 5 | 2 |
Windows Home Server | 5.2 | 5 | 2 |
Windows Server 2003 | 5.2 | 5 | 2 |
Windows XP Professional x64 Edition | 5.2 | 5 | 2 |
Windows XP | 5.1 | 5 | 1 |
Windows 2000 | 5.0 | 5 | 0 |