PEArmor 0.46 完美静态脱壳机

静态脱壳机源代码

程序界面:


 

感谢天草老大,提供 http://www.begin09.cn 这么好的一个学习环境。

 代码片段:

 

/*####################################################################
Filename:     PEArmor046UnPack.cpp
----------------------------------------------------
Remarks:    PEArmor0.46 Unpack Class
----------------------------------------------------
Author:        zhujian198  (就是 Jerson Ju)
Email:        zhujian198@163.com
zhujian198@gmail.com
Created:    5/3/2009
######################################################################

/*/////////////////////////////////////////////////////////////////////////

//     修复OEP

//////////////////////////////////////////////////////////////////////////
BOOL CPEArmor046UnPack::fixOEP()
{
    
    __try
    {
        
        DWORD oep 
= GETDWORD(shellstart2 + 0x2C8);
        
*(PDWORD((DWORD)pPEImage + 0x28)) = oep;
        
        fixSpecialApiEncode();
    }
    __except(EXCEPTION_EXECUTE_HANDLER)
    {
        
return FALSE;
    }
    
return TRUE;
}

//**************************************************************************
//按hying的说法,这里叫特殊代码处理
//**************************************************************************
BOOL CPEArmor046UnPack::fixSpecialApiEncode()
{

    
    __try{
        
        DWORD ApiIsEncode 
= GETDWORD(shellstart2 + 0x2BC);
        
        
if (ApiIsEncode == 1//是否特殊代码处理 FF 15 或 FF 25
        {
            
            
//修复Api 
            
            DWORD dwDecodeTable 
=  GETDWORD(shellstart2 + 0x2c4+ (DWORD)shellstart2;
            
while ( (*(PDWORD)dwDecodeTable) != 0)
            {
                DWORD dwDecodeVal 
= *(PDWORD)dwDecodeTable;
                
                dwDecodeVal 
= dwDecodeVal  << 1;
                dwDecodeVal 
= dwDecodeVal >> 1;
                
                
if( ( *((PBYTE)dwDecodeTable+3) ) == 0x80 )
                {
                    
//25ff
                    DWORD dwDecodeIAT = *(PDWORD)(dwDecodeTable + 4);
                    dwDecodeVal 
= dwDecodeVal - (DWORD)pe.ImageBase() + (DWORD)pImage;
                    
*((PWORD)(dwDecodeVal - 6)) = 0x25ff;
                    
*((PDWORD)(dwDecodeVal - 4)) = dwDecodeIAT;
                }
                
else
                {
                    DWORD dwDecodeIAT 
= *(PDWORD)(dwDecodeTable + 4);
                    dwDecodeVal 
= dwDecodeVal - (DWORD)pe.ImageBase() + (DWORD)pImage;
                    
*((PWORD)(dwDecodeVal - 6)) = 0x15ff;
                    
*((PDWORD)(dwDecodeVal - 4)) = dwDecodeIAT;
                }
                dwDecodeTable 
= dwDecodeTable + 8;
            }
            
        }
    }
    __except(EXCEPTION_EXECUTE_HANDLER)
    {
        
return FALSE;
    }
    
return TRUE;
}

//************************************************************************
//  拿分析的数据架构,构造导入表
//************************************************************************
    
BOOL CPEArmor046UnPack::fixImportTable()
{

    __try{
        
        DWORD dwDLLNumber 
= vecImport.size();
        BYTE 
* NewImportAddrSave = this->addNewImportSectionAddr;
        BYTE 
* temppoint = (BYTE *)(this->addNewImportSectionAddr+(dwDLLNumber + 1* sizeof(IMAGE_IMPORT_DESCRIPTOR));
        
for(vector<STOrgImport>::iterator it = vecImport.begin(); it != vecImport.end();++it)
        {
            
            IMAGE_IMPORT_DESCRIPTOR STNewIID 
= {0};
            
string strDllName = it->strdllName;
            strDllName.copy((
char *)temppoint,strDllName.length(),0);//复制到新增区域
            
// fill IID struct
            STNewIID.FirstThunk = it->dwThunkTable;
            STNewIID.Name 
= (DWORD)(temppoint-pImage);
            STNewIID.OriginalFirstThunk
=0;
            
            
            temppoint 
+= strDllName.length() + 1 + 2//加三个零
            
            PDWORD iat 
= (PDWORD)(STNewIID.FirstThunk + (DWORD)pImage);
            
            
//序号方式处理
            if (it->isOrd)
            {
                
for(vector<DWORD>::iterator itapi = it->vecApiOrd.begin(); itapi != it->vecApiOrd.end();++itapi)
                {
                    
*iat = *itapi | 0x80000000;
                    iat
++;
                }
            }
            
else //APi名字方式处理
            {
                
for(vector<string>::iterator itapi = it->vecApiName.begin(); itapi != it->vecApiName.end();++itapi)
                {
                    itapi
->copy((char *)temppoint,(*itapi).length());
                    
                    
*iat = temppoint - 2 - pImage;
                    iat
++;
                    temppoint 
+= (*itapi).length() + 1 + 2;//加三个零
                }
                
            }
            
*iat = 0;
            
            memcpy((PVOID)NewImportAddrSave,(PVOID)
&STNewIID,sizeof(IMAGE_IMPORT_DESCRIPTOR));
            NewImportAddrSave 
+= sizeof(IMAGE_IMPORT_DESCRIPTOR);
        }
        
        ((PIMAGE_NT_HEADERS)pPEImage)
->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress = this->addNewImportSectionAddr - pImage;
    }
    __except(EXCEPTION_EXECUTE_HANDLER)
    {
        
return FALSE;
    }
    
return TRUE;
}
///************************************************************************
//           分析,并且保持所有后面构造导入表所需信息,放入集合
//*************************************************************************

BOOL CPEArmor046UnPack::analyzeImportTable()
{

                
    __try{
        
        BOOL blApiStrShuffle  
= GETDWORD(shellstart2 + 0x2B8== 1?TRUE:FALSE;
        
        
        
if (blApiStrShuffle)  //IAT加密方式1
        {
            DWORD dwOrgImportaddr  
= GETDWORD(shellstart2 + 0x2c0+ (DWORD)shellstart2;
            
while (TRUE)
            {
                
if (GETDWORD((PDWORD)(dwOrgImportaddr))==0)
                {
                    
break;
                }
                STOrgImport stOrgImportDataTemp ;
                stOrgImportDataTemp.dwThunkTable 
= GETDWORD((PDWORD)(dwOrgImportaddr));
                stOrgImportDataTemp.strdllName.assign((
char *)(dwOrgImportaddr+5));
                stOrgImportDataTemp.dwApiNumber 
= GETDWORD((PBYTE)(dwOrgImportaddr + 5 + GETBYTE((PBYTE)(dwOrgImportaddr + 4)) + 1));
                dwOrgImportaddr 
= dwOrgImportaddr + 5 + GETBYTE(dwOrgImportaddr + 4+5;
                BOOL blIsApiOrd 
= GETBYTE(dwOrgImportaddr)==0?TRUE:FALSE;
                stOrgImportDataTemp.isOrd 
= blIsApiOrd;
                
if (blIsApiOrd) //序号
                {
                    
for (int i = 0 ; i < stOrgImportDataTemp.dwApiNumber;i++)
                    {
                        DWORD dwApiOrg 
= GETDWORD(dwOrgImportaddr+1);
                        stOrgImportDataTemp.vecApiOrd.push_back(dwApiOrg);
                        dwOrgImportaddr 
= dwOrgImportaddr + 1 + sizeof(DWORD) + 1;
                    }
                }
                
else  //APi名
                {
                    
for (int i = 0 ; i < stOrgImportDataTemp.dwApiNumber;i++)
                    {
                        
string strApiName;
                        strApiName.assign((
char *)(dwOrgImportaddr+1));
                        stOrgImportDataTemp.vecApiName.push_back(strApiName);
                        dwOrgImportaddr 
= dwOrgImportaddr + 1 + GETBYTE(dwOrgImportaddr)+1;
                    }
                }
                
                vecImport.push_back(stOrgImportDataTemp);
                
            }
            
        }
        
else  // IAT不自定义存储格式的 (IAT加密方式2)
        {
            DWORD dwDllBase 
= GETDWORD(shellstart2 + 0x2c0+ (DWORD)pImage;
            
            DWORD dwApiOrdOrName 
= NULL;
            DWORD dwIatAddr 
= NULL;
            
while(TRUE)
            {
                
                DWORD dwDllNameAddr 
= GETDWORD((PBYTE)dwDllBase + 0xc);
                
if (dwDllNameAddr != 0)
                {
                    
                    dwDllNameAddr 
= dwDllNameAddr + (DWORD)pImage; //dllname
                    
                    
                    
if (GETDWORD(dwDllBase) !=0)
                    {
                        dwApiOrdOrName 
= GETDWORD(dwDllBase) + (DWORD)pImage;
                        dwIatAddr 
= GETDWORD(dwDllBase + 0x10)+(DWORD)pImage;
                    }
                    
else
                    {
                        dwApiOrdOrName 
= GETDWORD(dwDllBase + 0x10+ (DWORD)pImage;
                        dwIatAddr 
= GETDWORD(dwDllBase + 0x10)+(DWORD)pImage;
                    }
                    
                    
                    STOrgImport stOrgImportDataTemp;
                    
if (GETDWORD(dwApiOrdOrName) & 0x80000000)
                    {
                        stOrgImportDataTemp.isOrd 
= TRUE;
                    }
                    
else
                    {
                        stOrgImportDataTemp.isOrd 
= FALSE;
                    }
                    stOrgImportDataTemp.dwThunkTable 
= dwIatAddr - (DWORD)pImage;
                    stOrgImportDataTemp.strdllName.assign((
char *)dwDllNameAddr);
                    
                    
                    
                    
while(TRUE)
                    {
                        
if (GETDWORD(dwApiOrdOrName) == 0)
                        {
                            dwDllBase 
= dwDllBase + 0x14;
                            
                            vecImport.push_back(stOrgImportDataTemp);
                            
break;
                        }
                        
else
                        {
                            
//处理
                            
                            
if ( GETDWORD(dwApiOrdOrName) & 0x80000000 )
                            {
                                DWORD dwOrd 
= GETDWORD(dwApiOrdOrName) & 0x7fffffff;
                                stOrgImportDataTemp.vecApiOrd.push_back(dwOrd);
                            }
                            
else
                            {
                                DWORD dwApiNameAddr 
= (GETDWORD(dwApiOrdOrName) + 2 ) + (DWORD)pImage;
                                
string strApiName;
                                strApiName.assign((
char *)dwApiNameAddr);
                                stOrgImportDataTemp.vecApiName.push_back(strApiName);
                            }
                            
                            dwApiOrdOrName 
= dwApiOrdOrName + 0x4;
                            
                            dwIatAddr 
= dwIatAddr + 0x4;
                        }
                    }
                    
                    
                }
                
else
                {
                    
break;
                }
            }
        }
        }
        __except(EXCEPTION_EXECUTE_HANDLER)
        {
            
return FALSE;
        }
        
return TRUE;
}

//********************************************************************************
//循环解压各个节
//********************************************************************************
BOOL CPEArmor046UnPack::unPackEachSection()
{

       __try
       {
           DWORD dwOffset 
= 0x2ED;
           
while (GETDWORD(shellstart2 + dwOffset)!=0)
           {
               DWORD dwCurrentSectionSize 
= GETDWORD(shellstart2 + dwOffset);
               HANDLE hEachSectionTempMem 
= VirtualAlloc(NULL,dwCurrentSectionSize, MEM_COMMIT, PAGE_READWRITE);
               DWORD dwEachSectionPackDataAddr 
= GETDWORD(shellstart2 + dwOffset + 0x4+ (DWORD)pImage;
               aP_depack_asm((PVOID)(dwEachSectionPackDataAddr),(PVOID)hEachSectionTempMem);
               memcpy((PVOID)dwEachSectionPackDataAddr,(PVOID)hEachSectionTempMem,dwCurrentSectionSize);
               VirtualFree(hEachSectionTempMem,dwCurrentSectionSize,MEM_RELEASE);
               dwOffset 
+= 0xC;
           }
       }
       
       __except(EXCEPTION_EXECUTE_HANDLER)
       {
           
return FALSE;
       }
       
return TRUE;
}

//*************************************************************************
//搜索特征码,在壳第一、二层找真正壳代码入口。
//*************************************************************************
BOOL CPEArmor046UnPack::verifyShell()
{
    
//*************************************************************************
    
//再次搜索特征码,在壳第一层找真正壳代码入口。
    
//*************************************************************************
    BYTE szPCode1[] = "\x5D\x81\xED\x05\x00\x00\x00\x8D\x75\x3D\x56";
    shellstart 
= searchMem(pPEImage,szPCode1,sizeof(szPCode1));
    
if (shellstart == NULL)
    {
        
return FALSE;
    }
    
    BYTE 
* FistPackBaseAddr = NULL;
    DWORD  dwFirstPackSize 
= 0;
       
    HANDLE hFistPackTempMem 
= 0;
    
       
//*************************************************************************
       
//再次搜索特征码,在壳第二层找真正壳代码入口。
       
//*************************************************************************
       __try
       {
           FistPackBaseAddr 
= shellstart - 0xAF;
           dwFirstPackSize  
= GETDWORD(FistPackBaseAddr + 0x82);
           hFistPackTempMem 
= VirtualAlloc(NULL,dwFirstPackSize, MEM_COMMIT, PAGE_READWRITE);
           aP_depack_asm((PVOID)(GETDWORD(FistPackBaseAddr
+0x7e)+FistPackBaseAddr),(PVOID)hFistPackTempMem);
       }
       __except(EXCEPTION_EXECUTE_HANDLER)
       {
           VirtualFree(hFistPackTempMem,dwFirstPackSize,MEM_RELEASE);
           
return FALSE;
       }
       
       
       BYTE szPCode2[] 
= "\xE8\x00\x00\x00\x00\x5A\x83\xEA\x05\x5D\xB9\x03\x00\x00\x00";
       
       shellstart2 
= searchMem((BYTE *)hFistPackTempMem,szPCode2,sizeof(szPCode2));
       
       
if (shellstart2 == NULL)
       {
           
return FALSE;
       }
       
       
return TRUE;
}

 

 

 

posted @ 2009-03-12 00:26  debugzhu  阅读(826)  评论(0编辑  收藏  举报