频道栏目
首页 > 资讯 > 系统安全 > 正文

再谈进程与端口的映射

04-10-06        来源:[db:作者]  
收藏   我要投稿

关于进程与端口映射的文章已经有很多了我把我对fport的分析也写出来让大家知道fport是如何工作的.
fport.exe是由foundstone team出品的免费软件可以列出系统中所有开放的端口都是由那些进程打开的.而下
面所描述的方法是基于fport v1.33的如果和你机器上的fport有出入请检查fport版本.

首先它检测当前用户是否拥有管理员权限(通过读取当前进程的令牌可知当前用户是否具有管理权限请参考
相关历程)如果没有打印一句提示后退出然后设置当前进程的令牌接着用ZwOpenSection函数打开内核对象
DevicePhysicalMemory这个对象用于对系统物理内存的访问.ZwOpenSection函数的原型如下:

NTSYSAPI
NTSTSTUS
NTAPI
ZwOpenSection(
Out PHANDLE sectionHandle;
IN ACCESS_MASK DesiredAccess;
IN POBJECT_ATTRIBUTES ObjectAttributes
};
(见ntddk.h)

第一个参数得到函数执行成功后的句柄
第二个参数DesiredAccess为一个常数可以是下列值:
#define SECTION_QUERY 0x0001
#define SECTION_MAP_WRITE 0x0002
#define SECTION_MAP_READ 0x0004
#define SECTION_MAP_EXECUTE 0x0008
#define SECTION_EXTEND_SIZE 0x0010

#define SECTION_ALL_ACCESS (STANDARD_RIGHTS_REQUIRED|SECTION_QUERY|
SECTION_MAP_WRITE |
SECTION_MAP_READ |
SECTION_MAP_EXECUTE |
SECTION_EXTEND_SIZE)
(见ntddk.h)
第三个参数是一个结构包含要打开的对象类型等信息结构定义如下:
typedef struct _OBJECT_ATTRIBUTES {
ULONG Length;
HANDLE RootDirectory;
PUNICODE_STRING ObjectName;
ULONG Attributes;
PVOID SecurityDescriptor; // Points to type SECURITY_DESCRIPTOR
PVOID SecurityQualityOfService; // Points to type SECURITY_QUALITY_OF_SERVICE
} OBJECT_ATTRIBUTES;
typedef OBJECT_ATTRIBUTES *POBJECT_ATTRIBUTES;
(见ntdef.h)
对于这个结构的初始化用一个宏完成:
#define InitializeObjectAttributes( p n a r s ) {
(p)->Length = sizeof( OBJECT_ATTRIBUTES );
(p)->RootDirectory = r;
(p)->Attributes = a;
(p)->ObjectName = n;
(p)->SecurityDescriptor = s;
(p)->SecurityQualityOfService = NULL;
}
(见ntdef.h)
那么打开内核对象DevicePhysicalMemory的语句如下:
WCHAR PhysmemName[] = L"\Device\PhysicalMemory";
void * pMapPhysicalMemory;
HANDLE pHandle;

bool OpenPhysicalMemory()
{
NTSTATUS status;
UNICODE_STRING physmemString;
OBJECT_ATTRIBUTES attributes;
RtlInitUnicodeString( &physmemString PhysmemName ); //初始化Unicode字符串函数原型见ntddk.h
InitializeObjectAttributes( &attributes &physmemString
OBJ_CASE_INSENSITIVE NULL NULL ); //初始化OBJECT_ATTRIBUTES结构
status = ZwOpenSection(pHandle SECTION_MAP_READ &attributes ); //打开内核对象DevicePhysicalMemory获得句柄
if( !NT_SUCCESS( status ))
return false;
pMapPhysicalMemory=MapViewOfFile(pHandleFILE_MAP_READ
00x300000x1000);
//从内存地址0x30000开始映射0x1000个字节
if( GetLastError()!=0)
return false;
return true;
}

为什么要从0x30000开始映射呢是这样我们知道在Windows NT/2000下系统分为内核模式和用户模式也就是我们
所说的Ring0和Ring3在Windows NT/2000下我们所能够看到的进程都运行在Ring3下一般情况下系统进程(也就是System
进程)的页目录(PDE)所在物理地址地址为0x30000或者说系统中最小的页目录所在的物理地址为0x30000.而页目录(PDE)由
1024项组成每项均指向一页表(PTE)每一页表也由1024个页组成而每页的大小为4K1024*4=4096(0x1000)所以上面从物
理地址0x30000开始映射了0x1000个字节.(具体描述见WebCrazy的文章<<小议Windows NT/2000的分页机制>>)

程序打开打开内核对象DevicePhysicalMemory后继续用函数ZwOpenFile打开内核对象DeviceTcp和DeviceUdpZwOpenFile
函数的原型如下:
NTSYSAPI
NTSTATUS
NTAPI
ZwOpenFile(
OUT PHANDLE FileHandle
IN ACCESS_MASK DesiredAccess
IN POBJECT_ATTRIBUTES ObjectAttributes
OUT PIO_STATUS_BLOCK IoStatusBlock
IN ULONG ShareAccess
IN ULONG OpenOptions
);
(见ntddk.h)

第一个参数返回打开对象的句柄
第二个参数DesiredAccess为一个常数可以是下列值:
#define FILE_READ_DATA ( 0x0001 ) // file & pipe
#define FILE_LIST_DIRECTORY ( 0x0001 ) // directory
#define FILE_WRITE_DATA ( 0x0002 ) // file & pipe
#define FILE_ADD_FILE ( 0x0002 ) // directory
#define FILE_APPEND_DATA ( 0x0004 ) // file
#define FILE_ADD_SUBDIRECTORY ( 0x0004 ) // directory
#define FILE_CREATE_PIPE_INSTANCE ( 0x0004 ) // named pipe
#define FILE_READ_EA ( 0x0008 ) // file & directory
#define FILE_WRITE_EA ( 0x0010 ) // file & directory
#define FILE_EXECUTE ( 0x0020 ) // file
#define FILE_TRAVERSE ( 0x0020 ) // directory
#define FILE_DELETE_CHILD ( 0x0040 ) // directory
#define FILE_READ_ATTRIBUTES ( 0x0080 ) // all
#define FILE_WRITE_ATTRIBUTES ( 0x0100 ) // all
#define FILE_ALL_ACCESS (STANDARD_RIGHTS_REQUIRED | SYNCHRONIZE | 0x1FF)
#define FILE_GENERIC_READ (STANDARD_RIGHTS_READ |
FILE_READ_DATA |
FILE_READ_ATTRIBUTES |
FILE_READ_EA |
SYNCHRONIZE)
#define FILE_GENERIC_WRITE (STANDARD_RIGHTS_WRITE |
FILE_WRITE_DATA |
FILE_WRITE_ATTRIBUTES |
FILE_WRITE_EA |
FILE_APPEND_DATA |
SYNCHRONIZE)
#define FILE_GENERIC_EXECUTE (STANDARD_RIGHTS_EXECUTE |
FILE_READ_ATTRIBUTES |
FILE_EXECUTE |
SYNCHRONIZE)
(见ntdef.h)
第三个参数是一个结构包含要打开的对象类型等信息结构定义见上面所述
第四个参数返回打开对象的属性是一个结构定义如下:
typedef struct _IO_STATUS_BLOCK {
union {
NTSTATUS Status;
PVOID Pointer;
};

ULONG_PTR Information;
} IO_STATUS_BLOCK *PIO_STATUS_BLOCK;

#if defined(_WIN64)
typedef struct _IO_STATUS_BLOCK32 {
NTSTATUS Status;
ULONG Information;
} IO_STATUS_BLOCK32 *PIO_STATUS_BLOCK32;
#endif
(见ntddk.h)
第五个参数ShareAccess是一个常数可以是下列值:
#define FILE_SHARE_READ 0x00000001 // winnt
#define FILE_SHARE_WRITE 0x00000002 // winnt
#define FILE_SHARE_DELETE 0x00000004 // winnt
(见ntddk.h)
第六个参数OpenOptions也是一个常数可以是下列的值:
#define FILE_DIRECTORY_FILE 0x00000001
#define FILE_WRITE_THROUGH 0x00000002
#define FILE_SEQUENTIAL_ONLY 0x00000004
#define FILE_NO_INTERMEDIATE_BUFFERING 0x00000008
#define FILE_SYNCHRONOUS_IO_ALERT 0x00000010
#define FILE_SYNCHRONOUS_IO_NONALERT 0x00000020
#define FILE_NON_DIRECTORY_FILE 0x00000040
#define FILE_CREATE_TREE_CONNECTION 0x00000080
#define FILE_COMPLETE_IF_OPLOCKED 0x00000100
#define FILE_NO_EA_KNOWLEDGE 0x00000200
#define FILE_OPEN_FOR_RECOVERY 0x00000400
#define FILE_RANDOM_ACCESS 0x00000800
#define FILE_DELETE_ON_CLOSE 0x00001000
#define FILE_OPEN_BY_FILE_ID 0x00002000
#define FILE_OPEN_FOR_BACKUP_INTENT 0x00004000
#define FILE_NO_COMPRESSION 0x00008000
#define FILE_RESERVE_OPFILTER 0x00100000
#define FILE_OPEN_REPARSE_POINT 0x00200000
#define FILE_OPEN_NO_RECALL 0x00400000
#define FILE_OPEN_FOR_FREE_SPACE_QUERY 0x00800000
#define FILE_COPY_STRUCTURED_STORAGE 0x00000041
#define FILE_STRUCTURED_STORAGE 0x00000441
#define FILE_VALID_OPTION_FLAGS 0x00ffffff
#define FILE_VALID_PIPE_OPTION_FLAGS 0x00000032
#define FILE_VALID_MAILSLOT_OPTION_FLAGS 0x00000032
#define FILE_VALID_SET_FLAGS 0x00000036
(见ntddk.h)

那么打开内核对象DeviceTcp和DeviceUdp的语句如下:
WCHAR physmemNameTcp[]=L"\Device\TCP";
WCHAR physmemNameUdp[]=L"\Device\UDP";
HANDLE pTcpHandle;
HANDLE pUdpHandle;

HANDLE OpenDeviceTcpUdp(WCHAR * deviceName)
{
NTSTATUS status;
UNICODE_STRING physmemString;
OBJECT_ATTRIBUTES attributes;
IO_STATUS_BLOCK iosb;
HANDLE pDeviceHandle;

RtlInitUnicodeString(&physmemString deviceName);
if(GetLastError()!=0)
return NULL;
InitializeObjectAttributes( &attributes&physmemString
OBJ_CASE_INSENSITIVE0 NULL );
status = ZwOpenFile ( &pDeviceHandle0x100000 &attributes &iosb 30);
if( !NT_SUCCESS( status ))
return NULL;
}

接着程序用ZwQuerySystemInformation函数获得系统当前所以进程的所建立的句柄及其相关信息函

相关TAG标签
上一篇:Administrastor真不安全
下一篇:《再谈进程与端口的映射》之续篇
相关文章
图文推荐

关于我们 | 联系我们 | 广告服务 | 投资合作 | 版权申明 | 在线帮助 | 网站地图 | 作品发布 | Vip技术培训 | 举报中心

版权所有: 红黑联盟--致力于做实用的IT技术学习网站