谈谈高手的成长和黑软的编写过程
作者 宋柏思(网名:谷夕、gxisone)
“谈谈高手的成长”,这句话大家看来也许会认为我是一个编程高手,说实话,其实我也算不上是真正的高手,只是比大家先走一步和多走一步而已。曾经很多人问我如何才能够成为编程高手,如何才能够编写出优秀的程序。我认为,真正的高手不是你去编两行代码或者是几分钟写几行代码等。精通C语言就算是高手么?未必。就像你煎荷包蛋煎得很好,你就能叫做烹饪大师么?真正的编程高手不仅能够精通某种语言,而且能够清楚了解操作系统的原理和怎样来利用手中的语言来更好地控制系统。那么,高手是怎样成长过来的呢?
我认为,首先还是要熟悉一种语言,例如C、C++、pascal等。为什么不说C#和JAVA呢?要知道JAVA和C#等都是为了方便开发人员而建立的一种体系,语言本身越方便了,离系统底层就越远了。所以,如果大家想成为编程高手还是从C/C++入手吧。另外还是强调要从C入手,有了C的基础学C++也会比较容易点,另外更重要的一点是因为所有的API都是C函数,所谓的MFC只是这些API函数的一个封装。我们掌握C语言,基本上就可以开始我们的编写黑软的“生涯”了。怎样才算是掌握C语言?最简单的就是,你精通指针了么?C语言的精粹就在于指针。还有字符串的操作熟练了么?如果这两种都不熟悉的话,我还是劝你回去再巩固巩固这方面的内容,否则以后会碰很多钉子的。另外,这里说是开始,是因为语言本身只是一种工具,你要掌握的还多呢。当你能够让一种语言很好的为你服务时,你就要开始掌握系统的接口,也就是API函数。当API函数也积累不少了,那么就可以进行一些小的开发了。例如想开发网络方面的程序,socket编程熟悉了么?TCP/IP协议熟悉了么?总之,知识的覆盖面要广,广了然后再深,这样才能够让自己不断的进步,最终成为高手。
成为了编程高手要做什么?那当然是开发程序了,否则学那么多东西干嘛?那么程序(黑软)又是怎样开发出来的呢?下面就以我自己的经历为大家简单做一下介绍,希望对广大X读者有启迪的作用吧。
俗话说“好的开始是成功的一般”,那么,究竟如何开始着手编写黑客软件呢?
首先,你得先想想你编写黑客软件的目的是什么。可能有人会问:“现在网上有那么多的黑客工具,用得着自己编写么?”的确,现在网络的发达给大家提供了极大的方便,很多傻瓜式的黑软遍地都是,但是,你甘心一辈子都做个tool kid么?只懂得使用别人开发的工具算得了什么?记得当初本人写了ICMP后门,发布后反应很大。但不久很多人说该后门被杀毒软件查杀了,期待新的版本出现,并寄他一份。但却是很少人叫我要求源码或是请教问题什么的。现在还有人追求技术的吗?还是大家都在跟着潮流玩玩木马、搞搞dos和看者别人的文章照样子去搞搞破坏?
不好意思,扯远了。
其实黑客工具的编写者编写黑客工具的目的无非是让自己在网上出出名或者赚点钱而已。好的木马或其它黑软用的人多了,作者名气肯定会增加,然后有些作者就开始收费了。有了这两个目的,就驱使黑软作者去编写黑客软件了。
我们来看看黑软的编写过程吧(这个是我写程序时的过程,也许其它高手会有他们更好的方法哦)首先,要确定写什么,而不是什么都想写。木马现在多得很,如果你认为你写的木马能够打败现在网上流行的,那你就大胆去写吧,后门也一样,否则,我还是劝你去找找缺口,发挥自己的想像和创新能力去编写与众不同的东西(当然,平时可以编写一些小的程序来学习学习)。
一但确定了自己想要开发什么,那就要寻找合适的开发语言和开发工具了。当然,要选用自己熟悉的语言和工具啦。对于编程新手而言,可能他会觉得C语言开发的用VB也可以实现,而且看起来很不错。而稍有经验的人来说呢,就会选择C语言来直接使用API。这时,做出来的效果同样不错,而且性能良好。到了成为高手时,他就不会首先选择哪些工具了,而是考虑怎样才是最快最有效率的。编写程序和其它不同,在要实现某种功能时,有N种办法,但在这N种办法中,只有一种或两种是最好最快的。
确定了语言和工具后,就要考虑如何实现黑软的功能了。这个时候,我们应该一个部分一个部分拆开来,也就是把要实现的功能写成一个个函数,最后在主函数里调用这些函数。任何一个程序,如果它本身的复杂度越大,它出错的几率就会越大。当我们把程序拆成很多小函数时,每个函数出错的几率就缩小了,而且调试起来也比较容易。把要实现的功能写成一个个函数还有其它的好处,就是如果以后写其它程序时,当需要实现某一功能,我们就可以把以前写好的函数稍为修改或者直接调用就行了。利用这种办法,程序才能够容易地做出1.0、1.1、2.0版。否则做完1.0后,要做1.1版时又要全部重做,这会浪费多少的时间和精力?
另外,我们应该首先把最重要的部分写好,看看能不能够实现。如果你一开始编写了其它功能的模块,但到最后发现最主要的功能实现不了,那么整个程序就会“流产”了,那么多的时间和精力白费了。就拿那个ICMP后门的开发过程来说,我首先是要确定能够利用ICMP进行通信,其它的东西都是其次,这个通信问题解决不了,还谈什么其它功能?当我通过测试的确能够利用ICMP进行通信时,那么我们再写其它功能的模块,到最后就把所有的东西拼起来。这个过程可以简单的概括如下:
1. 确定程序的核心功能
2. 查找出最基本的可用的API函数(必要时自己编写其它的函数)
3. 确保最重要的核心能够实现,然后逐一测试完成各个模块
4. 各个模块可以实现了吗?可以的话就进行拼接,否则可以考虑其它的实现方法或者干脆去掉这个功能。
5. 进行最后的测试
一旦我们确定了要写软件了,那么就应该尽快开始和连续的写。这个连续不是叫你几天几夜废寝忘食地写,起码你每天要完成一点点。千万不要写一个星期停一个星期或者写了一些又停下来写一些其它的东西,如果这样,思路很容易会断掉,而且热情也很可能会消去。我当初写ICMP后门时,是连续写了十几天,那段时间,基本上都是围绕这个后门要实现的功能来写的。另外,平常很多时候如果我们突然有灵感要实现某些功能或者想到某些技巧时,应该就立刻把它记下来,否则灵感就这样跑掉了。其实,对于一个程序编写者来说,真正重要的不在于代码怎么写,关键是创意和思路的问题。别人写的东西有创意,这创意从哪里来?就是突然来的灵感啊!光学会多想还不行,想到了还要记下来,记下来了还要懂得怎样去做。否则,想到了没有去实现有什么用?
对于我们简单的编写黑软来说,编码使用的时间最长。没有哪为同志写个木马要运用到软件工程把?所以,我们写软件其实就是编代码。但是没有人可以一下子就能够写出准确无误的代码来(Hello world!的例子除外),而往往是写一段代码就需要调试一下。可以肯定的说,所有的代码都是调试出来的,而不是“编”出来的,只有经过调试的代码才能保证它是可用的。因此,调试的技巧也就要掌握一些了。对于我来说,在编写程序时也会往往出现错误的。遇到错误时,首要问题当然就是要找出是哪里产生的错误。一个很好的办法就是,我们应该在可能出现错误的地方利用printf()函数(如果是窗口程序可以利用MessageBox函数)来给出提示。当然,这是调试过程中用到的办法,在确保程序不会出现严重错误后,就可以把这些输出信息的语句注释调。大家也不希望后门或木马出错时给用户一个提醒吧?除了利用printf()函数,还可以利用VC里的断点设置。例如某段代码编译成exe程序后,执行它出现错误(C程序里常见的错误,就是通过编译,但运行时出现错误),那么我们可以在某行代码上下一个断点(不会下断点?在光标所在行按F9),然后进行调试,如果没事,证明断点之前的代码是没问题的;如果又出现错误了,那么我们就应该把断点向前移,这样可以找出引起错误的那行代码(当然,这是相对于代码比较少的情况而言)。另外,我们还应该在调试中积累经验,例如指针指向了不能访问的内存而导致错误了,那么应该马上联想到哪里用到指针,十有八九就是那里出问题了。
在编写代码过程中,调试固然重要,但还有一点要注意的就是合理地加上注释。为什么说合理地加上注释呢?我们没必要每一行都加上注释,如果这样的话代码的可读性也是很差的。我们应该在别人容易误解或自己容易忘记的地方加上注释。这样可以防止以后自己再看这段代码时忘记了这段代码是干什么的。其实这样的事很常见,就是几个月前专心于某些代码,之后写了其它代码后,再看回之前的一些代码往往就有些地方不明白了,所以注释是很重要的。注释重要,代码的规范也同样重要。开发一个程序不是一、两天就可以搞定的,所以你得让你的代码保持可读性,也就是今天写的代码,明天还可以看清楚。我们写代码时都会保持一种状态,那就是下一步应该干什么。如果代码规范,即使我停了一两天,过几天接下去还可以一看就明白下一步该做什么。很多人编写程序时,只想着快点完成,代码杂乱无章,当程序写得差不多时,才发现这里出现问题,那里也出现问题,别人看不懂,甚至过了一段时间自己也看不懂,这样的代码如何维护?如何给别人作为参考?网上有很多高手写的代码,打开一看,你就会发现的确不一样,给人的是清晰的感觉。有个朋友发他写的代码给我看,我只看了前面的一些变量定义就没勇气再看下去了(毕竟我的大脑不是编译器哦),我择抄部分给大家看看(希望这位朋友不要介意哦,我没有批评你的意思,只是给大家举个例子而已):
struct{char target[255];char dostype;char faketype;HANDLE threadhandle;HANDLE timerhandle;
int pausetime;int seconds;int definemins;WORD attackport;WORD useport;}dos;
HANDLE filefp;HANDLE pbitmapwithoutfileh;DWORD sizeimage;unsigned int packnum=0;
……
DWORD WINAPI threadfunc( LPVOID lpParam )
{char workflag=0;int recvlen=0;SOCKET socktcp;socktcp=*((SOCKET*)lpParam);
while(1){memset(buff,0,66000);recvlen=recv(socktcp,buff,66000,0);
if(strncmp(buff,pwd,strlen(pwd))){closesocket(socktcp);workflag=0;return 0;}//solve pwd
int duelen;memcpy(&duelen,buff+28,4);
while(duelen>recvlen){recvlen+=recv(socktcp,buff,66000,0);}//solve data division
int sendlength=65536;workflag=work(buff+32,duelen-32,workflag,&sendlength);
sendlength+=32;memcpy(buff+28,&sendlength,4);
if(sendlength!=send(socktcp,buff,sendlength,0)){closesocket(socktcp);workflag=0;return 0;}
}
}
这样的代码别说给别人看了,可能时间隔了长一点自己也不会看得明白(也许除了编译器能够看明白,呵呵)。我们写程序的源码要减少篇幅么?这样写效率高些么?还是要跟别人比比谁的程序更短?我不建议大家学习上面的风格,起码一个结构要写成下面的样子才让人看得舒服点嘛:
struct{
char target[255];
char dostype;
char faketype;
HANDLE threadhandle;
HANDLE timerhandle;
int pausetime;
int seconds;
int definemins;
WORD attackport;
WORD useport;
}dos;
最好还给每个变量加上注释。另外,“{”和“}”应该单独占一行的,而且当大家写了“{”后应该马上再写个“}”,这样才能够保证代码时刻都处于可编译状态。如果写了N个“{”后,再去一个一个补“}”,你知道要补多少个?你知道哪个“}”是对哪个“{”?也许你知道,但我不知道。
源码编写好了,也编译出exe文件了,那么就先发给你的一些好朋友试一下吧。一方面可以炫耀一下自己的作品:),另一方面可以叫他们帮手找找bug,确保没什么大问题后就可以上网发布了。这样,又一个黑软诞生了!
程序出来了,如果不想作为商业用途,那么源代码还是共享给大家比较好,毕竟可以帮助别人,而且也许别人会从你的代码中发现错误然后帮你改正了。另外,你共享代码给别人了,或者哪一天他也通过你的代码编了个更好的程序,我想他也会毫无保留的寄你源码,我就试过这种情况了。那是一个外国朋友向我要源码,来信中他也说了如果程序改进了会发给我一份,结果不久就会收到他的回复。可惜的是这种做法在我们这里并不那么流行哦。其实,你做个木马,只要不是打算拿去卖,那么你保留它的源码又有什么用呢?难道这样会变成钞票么?现在都是提倡开源啊。大家看完这些,如果日后成为高手或者是有作品出来的一刻,是不是也应该贡献出来让大家一起进步呢?
好了,X的读者们,是否有冲动现在就准备开发你的第一个黑软呢?心动不如行动了,发挥你的创意来编写出一个个优秀的黑软吧!
- 设计能向 Apple 学什么?. 2007-11-01 03:50
- 中国黑客10年 2007-11-01 05:15
- 通过对HDWiki程序代码分析. 2007-10-28 21:40
- About 2007-10-19 13:23
- 交换友情连接 2007-10-19 19:38
- 漏洞的形成和防治 2007-10-27 15:22
- 安全漏洞 2007-10-25 20:39
- 各种网站程序的默认数据库. 2007-10-27 22:33
- ASP常见的安全漏洞 2007-10-27 17:03
- 四大漏洞可轻松入侵博客. 2007-10-25 22:50
- 如何成为一名黑客 2007-11-16 15:46
- 帮助 2007-10-19 13:55
| 更多 | ||||||||||||
|
||||||||||||