文件名:PEView
//打开文件并创建内存文件映像 //内存文件映像的作用是把整个文件映射入进程的虚拟空间中,这样操作文件就像操作内存变量或数据一样的方便 bool CPEViewDlg::FileCreate(char *szFileName) { bool bRet = FALSE; m_hFile = CreateFile(szFileName, GENERIC_READ | GENERIC_WRITE, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL); if( m_hFile == INVALID_HANDLE_VALUE) { return bRet; } m_hMap = CreateFileMapping(m_hFile , NULL, PAGE_READWRITE | SEC_IMAGE, 0 , 0 ,0); if( m_hMap == NULL) { CloseHandle(m_hFile); return bRet; } m_lpBase = MapViewOfFile(m_hMap , FILE_MAP_READ | FILE_MAP_WRITE , 0, 0 ,0); if( m_lpBase == NULL) { CloseHandle(m_hMap); CloseHandle(m_hFile); return bRet; } bRet = TRUE; return bRet; } //判断文件是否为有效的PE文件,得到解析PE格式的相关结构体的指针 bool CPEViewDlg::IsPeFileAndGetPEPointer() { bool bRet = FALSE; m_pDosHdr = (PIMAGE_DOS_HEADER)m_lpBase; if( m_pDosHdr->e_magic != IMAGE_DOS_SIGNATURE) return bRet; m_pNtHdr = (PIMAGE_NT_HEADERS)((DWORD)m_lpBase + m_pDosHdr->e_lfanew); if(m_pNtHdr->Signature != IMAGE_NT_SIGNATURE) return bRet; m_pSecHdr = (PIMAGE_SECTION_HEADER)((DWORD)&(m_pNtHdr ->OptionalHeader) + m_pNtHdr ->FileHeader.SizeOfOptionalHeader); bRet = TRUE; return bRet; } //解析PE格式 void CPEViewDlg::ParseBasePe() { CString StrTmp; //入口地址 StrTmp.Format("%08X" , 4567); StrTmp.Format("%08X" , m_pNtHdr->OptionalHeader.AddressOfEntryPoint); SetDlgItemText(IDC_EDIT_EP,StrTmp); //映像地址 StrTmp.Format("%08X",m_pNtHdr->OptionalHeader.ImageBase); SetDlgItemText(IDC_EDIT_IMAGEBASE,StrTmp); //连接器版本号 StrTmp.Format("%d.%d", m_pNtHdr->OptionalHeader.MajorLinkerVersion, m_pNtHdr->OptionalHeader.MinorLinkerVersion); SetDlgItemText(IDC_EDIT_LINKVERSION,StrTmp); //节表数量 StrTmp.Format("%02X",m_pNtHdr->FileHeader.NumberOfSections); SetDlgItemText(IDC_EDIT_SECTIONNUM,StrTmp); //文件对齐值大小 StrTmp.Format("%08X",m_pNtHdr->OptionalHeader.FileAlignment); SetDlgItemText(IDC_EDIT_FILEALIGN,StrTmp); //内存对齐值大小 StrTmp.Format("%08X",m_pNtHdr->OptionalHeader.SectionAlignment); SetDlgItemText(IDC_EDIT_SECALIGN,StrTmp); } void CPEViewDlg::EnumSections() { int nSecNum = m_pNtHdr->FileHeader.NumberOfSections; int i = 0; CString StrTmp; for( i = 0; i < nSecNum; i++) { m_SectionList.InsertItem(i,(const char*)m_pSecHdr[i].Name); StrTmp.Format("%08X" , m_pSecHdr[i].VirtualAddress); m_SectionList.SetItemText(i,1,StrTmp); StrTmp.Format("%08X" , m_pSecHdr[i].Misc.VirtualSize); m_SectionList.SetItemText(i,2,StrTmp); StrTmp.Format("%08X" , m_pSecHdr[i].PointerToRawData); m_SectionList.SetItemText(i,3,StrTmp); StrTmp.Format("%08X" , m_pSecHdr[i].SizeOfRawData); m_SectionList.SetItemText(i,4,StrTmp); StrTmp.Format("%08X" , m_pSecHdr[i].Characteristics); m_SectionList.SetItemText(i,5,StrTmp); } } void CPEViewDlg::OnBtnView() { // TODO: Add your control notification handler code here CString str; GetDlgItemText(IDC_EDIT_PATH,str); FileCreate((LPSTR)(LPCTSTR)str); IsPeFileAndGetPEPointer(); ParseBasePe(); EnumSections(); } void CPEViewDlg::InitList() { m_SectionList.SetExtendedStyle(m_SectionList.GetExtendedStyle() | LVS_EX_GRIDLINES | LVS_EX_FULLROWSELECT); m_SectionList.InsertColumn(0,_T("节名")); m_SectionList.InsertColumn(1,_T("V.偏移")); m_SectionList.InsertColumn(2,_T("V.大小")); m_SectionList.InsertColumn(3,_T("E.偏移")); m_SectionList.InsertColumn(4,_T("R.大小")); m_SectionList.InsertColumn(5,_T("标志")); m_SectionList.SetColumnWidth(0,LVSCW_AUTOSIZE_USEHEADER); m_SectionList.SetColumnWidth(1,LVSCW_AUTOSIZE_USEHEADER); m_SectionList.SetColumnWidth(2,LVSCW_AUTOSIZE_USEHEADER); m_SectionList.SetColumnWidth(3,LVSCW_AUTOSIZE_USEHEADER); m_SectionList.SetColumnWidth(4,LVSCW_AUTOSIZE_USEHEADER); m_SectionList.SetColumnWidth(5,LVSCW_AUTOSIZE_USEHEADER); }