首页
社区
课程
招聘
[翻译]29A杂志#8:编译迷你Win32可执行文件(使用C代码)
发表于: 2006-2-6 16:34 10574

[翻译]29A杂志#8:编译迷你Win32可执行文件(使用C代码)

2006-2-6 16:34
10574

不知道哪位前辈帮忙开通一下上传附件功能~谢谢

[声明] By Anskya
初学翻译,由于英语基础和写作风格的差异,可能导致译文与原文的一些差异
如有不明请阅读原文,谢谢大家支持....
为了更适合大家阅读和理解文章内容这里将使用一些比较容易理解的语句
请大家不要责怪小弟翻译水平不好.(原文直接翻译会令人非常费解)

由于本人能力有限,翻译过程中难免会出现错误,请大家指正,
写希望大家多多交流,谢谢各位支持和看完此文,转载请保留版权
[By Anskya] Email:Anskya@Gmail.com QQ:115447

//-------------------------------------------------
编译迷你Win32可执行文件(使用C代码)
作者:DoxtorL.,西元 2004年

如今人们使用各类加壳软件程序压缩应用程序使自己的程序更短小,
使得大家都忽略(原文:是否因为懒惰?)了如何自己编译一个小巧的二进制文件,
希望下面所讲述的可以给你一些思路..
(个人理解是这个意思~不明的地方看原文~这里只是依照个人思维翻译的)

摘要:
简介.
第1讲.不使用代码,定位代码入口点和C语言连接时间库(就是*.lib)
第2讲.融合PE节
第3讲.使用Dos stub(DOS插桩柱)来存储初始化数据(可以解释成常量!)
第X讲.再进一步......等等....

源代码:test.c,test2.c

介绍:
编译迷你的应用程序是建立在一个好的连接器基础上的.
这里我使用的是Pelles-c的连接库
(译者注:Pelles-c,类似LCC的一种C语言编译器,其实就是LCC源代码修改的)
Pelles-c是一款免费很不错的编译器(只支持C语言)Polink(指的是连接器)
是模拟科隆M$ VC的连接器的.

我使用一个"Hello World"程序(test.c)来示范编译一个迷你的应用程序.
(原文意思是~我应该用次来优化一个二进制文件...不理解他是什么意思)

***** 第0讲: 默认编译
使用命令:
cc.exe test.c
polink.exe c:\progra~1\pellesc\lib\crt.lib c:\progra~1\pellesc\ ->
lib\win\kernel32.lib test.obj

result: test.exe ,size=27648 bytes
这个体积有点大了,但是程序只使用了Kernel32.dll中的函数
***** 第1讲:
不使用代码,重定位代码入口点和C语言连接时间库(就是*.lib),
连接器使用一个常规的入口点,代码功能:读取和解析附加参数.

我们的例子不需要上面的特征(命令),为了优化我们的代码我们决定去除这些东西

.
连接器有个参数:

/ENTRY: <symbol>        

(/ENTRY:后面跟程序入口函数--一般我们的程序是main开始的)

symbol是你的程序main函数的入口点(译者注:当然你也可以设置成别的函数例如:

/ENTRY:MyMain)
如果我们需要使用一个C连接库可以使用:

/NODEFAULTLIB

编译命令:

cc.exe test.c
polink.exe /NODEFAULTLIB /ENTRY:main

c:\progra~1\pellesc\lib\win\msvcrt.lib test.obj

result: test.exe, size=2560 bytes

***** 第2讲:融合PE节
(译者注:许多加壳软件加壳后程序的节明显比原来小了.这里所说的就是这个意思

)
我们的test.exe程序编译后拥有2个PE节: .text ,.rdata ,.data
我们可以融合三个节成为一个节

连接器设置:  /MERGE:<source section>=<destination section>

(原文:this option can be used several times!,感觉无意义就没有翻译)

编译命令:

cc.exe test.c
polink.exe /MERGE:.rdata=.text /MERGE:.data=.text /NODEFAULTLIB

/ENTRY:main ->
c:\progra~1\pellesc\lib\win\msvcrt.lib test.obj

result: test.exe, size=1536 bytes

***** 第3讲:使用Dos stub(DOS插桩柱)来存储初始化数据
DOS Stub头部是PE程序为了兼容msdos系统所作的,如果你的程序的程序
在msdos环境下运行,会显示一个"This program cannot be run in DOS mode"
的警告信息然后退出.(译者注:就和printf打印这条信息一个结果~不过他使用的

是int21中断)
他可以作一些你需要让程序在dos下作的事情(那是你自己的事情这里就不细说了)
dos stub尺寸是512的倍数,最小的可能性也是512字节,如果我们去除警告信息dos

stub
只有160字节,剩下的空间可以用来存储我们的初始化数据(译者注:许多DIY PE的

牛人都作过小于
512字节的dos stub..似乎原作者认为dos stub必须是512字节不然就会发生什么

事情..:P)

我们必须改变少量的C代码,

我们需要将数据分成两个部分,一个部分保存在dos

stub中,剩下的部分保存在.text段中.

Polink连接器可以设置我们需要使用的dos stub.这里我们用一个免费的汇编语言

编译器FASM来作
(译者注:B人很喜欢的一个编译器,开源,有大量的宏指令可以使用,由于是低级编

译器可以按照自己的设想编译PE结构)

编译器设置参数: /STUB:<my dos stub> ,这里设置我们需要的dos stub 的二进

制文件(这么说话好别扭~:D)

编译命令:

fasm stub.asm stub.bin
cc.exe testb.c
polink.exe /STUB:stub.bin /MERGE:.rdata=.text /MERGE:.data=.text

/NODEFAULTLIB /ENTRY:main ->
c:\progra~1\pellesc\lib\win\msvcrt.lib testb.obj

*****第X讲:再进一步
(译者注:dos stub中)可以保存你需要导入的DLL的函数名和~"By Name"等等字符

串信息
(似乎好多壳都这样作了~比如(Win)Upack,FSG等等壳),一般使用导入序数不是一

个好主意,
因为操作系统的差别~(译者注:比如Win2k,WinXp,Win9x下的函数未必就是一个序

号.大家需要注意这里)
总之..一些DLL,如wsock32.dll,你完全没有必要在Windows下使用序数....
对导入表使用序数,你需要使用一些特别的方法导入连接库....
一个不需要使用代码的方法,在你连接程序的创建导入表列表的方法.
polib.exe这个工具可以创建你连接库的导入表保存成一个 .def的文件
这里是一个演示的文件:
***** example of a .def file
LIBRARY WSOCK32
EXPORTS
accept @1
bind @2
closesocket @3
connect @4
htons @9
listen @13
recv @16
send @19
socket @23
gethostbyname @52
WSAAsyncSelect @101
WSACleanup @116
WSAStartup @115
***** end of file
.def文件保存了我们需要导入的wsock32.dll的函数,不是全部只有我们需要的
<symbols> @XXX
symbols是设置我们需要使用的函数名称-.xxx 是我们需要导入的函数序数
polib.exe同时会创建一个.lib 的文件
改变PE字节的一种BT方法(译者注释:原文翻译是这样:获取文件数据的一种BT方法

.)
,一个PE文件必须是512的倍数(老毛病又犯了.)
和一些小于1024字节的程序还是可以和Win32相兼容的.
(译者注:这里说的是文件对齐~512字节,一开始我也没看懂以后看了下面的代码

才明白)
这个方法是:调整PE文件的对齐字节(设置成512的倍数--当然也可以是使用512)
这样调整后,文件的第一个节的虚拟地址偏移+大小就是文件的大小(接近于1000h

的倍数.也可以是1024)
(译者注:剩下的部分原作者都没有写~也许是我翻译的有问题,反正就没了~呵呵

不知道是什么意思)

以下为源代码
/***** test.c*/
#include <stdio.h>

#define POEM "\
It might be lonelier\r\n\
Without the Loneliness --\r\n\
I'm so accustomed to my Fate --\r\n\
Perhaps the Other -- Peace --\r\n\r\n\
Would interrupt the Dark --\r\n\
And crowd the little Room --\r\n\
Too scant -- by Cubits -- to contain\r\n\
The Sacrament -- of Him --\r\n\r\n\
I am not used to Hope --\r\n\
It might intrude upon --\r\n\
Its sweet parade -- blaspheme the place --\r\n\
Ordained to Suffering --\r\n\r\n\
It might be easier\r\n\
To fail -- with Land in Sight --\r\n\
Than gain -- My Blue Peninsula --\r\n\
To perish -- of Delight --\r\n\r\n\
(Emily Dickinson, 1830-1886)\r\n"

void main()
{
printf(POEM);
}
/***** End of source code*/

/***** test2.c*/
#include <stdio.h>

#define PTR_POEM1 0x400040

#define POEM2 "\
little Room --\r\n\
Too scant -- by Cubits -- to contain\r\n\
The Sacrament -- of Him --\r\n\
I am not used to Hope --\r\n\
It might intrude upon --\r\n\
Its sweet parade -- blaspheme the place --\r\n\
Ordained to Suffering --\r\n\r\n\
It might be easier\r\n\
To fail -- with Land in Sight --\r\n\
Than gain -- My Blue Peninsula --\r\n\
To perish -- of Delight --\r\n\r\n\
(Emily Dickinson, 1830-1886)\r\n"

void main()
{
printf("%s%s",PTR_POEM1,POEM2);
}
/***** End of source code*/

作者原文没有帖FASM部分的代码我这里补上
下载最新的FASM版本然后直接编译就好了,会生成一个stub.bin文件
请自行修改成stub.exe然后在按照上面所说的文章进行编译就可以了
/***** stub.asm*/
DOS_Header:
   .e_magic     dw "MZ"      ;IMAGE_DOS_SIGNATURE
   .e_cblp      dw 0x0080
   .e_cp        dw 0x0001
   .e_crlc      dw 0x0000
   .e_cparhdr   dw 0x0004
   .e_minalloc  dw 0x0010
   .e_maxalloc  dw 0xFFFF
   .e_ss        dw 0x0000
   .e_sp        dw 0x0140
   .e_csum      dw 0x0000
   .e_ip        dw 0x0000
   .e_cs        dw 0x0000
   .e_lfarlc    dw 0x0040
   .e_ovno      dw 0x0000
   .e_res       rw 4
   .e_oemid     dw 0x0000
   .e_oeminfo   dw 0x0000
   .e_res2      rw 10
   .e_lfanew    dd PE_header  ;PE header Offset

DOS_Stub:
org $+DOS_Stub

POEM1 db "It might be lonelier",0dh,0ah
      db "Without the Loneliness --",0dh,0ah
      db "I'm so accustomed to my Fate --",0dh,0ah
      db "Perhaps the Other -- Peace --",0dh,0ah,0dh,0ah
      db "Would interrupt the Dark --",0dh,0ah
      db "And crowd the",0

rb 160-(DOS_Stub-$)
PE_header:
/***** End of source code*/

由于本人能力有限,翻译过程中难免会出现错误,请大家指正,
写希望大家多多交流,谢谢各位支持和看完此文,转载请保留版权
[By Anskya] Email:Anskya@Gmail.com QQ:115447


[注意]传递专业知识、拓宽行业人脉——看雪讲师团队等你加入!

收藏
免费 7
支持
分享
最新回复 (3)
雪    币: 47147
活跃值: (20450)
能力值: (RANK:350 )
在线值:
发帖
回帖
粉丝
2
最初由 Anskya 发布
不知道哪位前辈帮忙开通一下上传附件功能~谢谢


论坛程序有些问题,晚上回去修复,到时你再来上传附件。
2006-2-6 16:44
0
雪    币: 47147
活跃值: (20450)
能力值: (RANK:350 )
在线值:
发帖
回帖
粉丝
3
最初由 kanxue 发布

论坛程序有些问题,晚上回去修复,到时你再来上传附件。


你可以上传附件了。
2006-2-6 20:32
0
雪    币: 339
活跃值: (1510)
能力值: ( LV13,RANK:970 )
在线值:
发帖
回帖
粉丝
4
29a的杂志质量也越来也不好了,好久也没出新杂志了。比较汉
2006-2-7 17:29
0
游客
登录 | 注册 方可回帖
返回
//