C前面看了一大段是不是有点云里雾里的啊?是有点罗嗦但是俗话说万事总是开头难OK现在总算可以写主程序文件了
下面就是antc文件
#include anth
#include signalh
//表示不用表示用代理
int use_proxy;
//代理服务器的地址
char proxy_server[];
//端口
u_short proxy_port;
//蚂蚁数目
int ant_num;
//下载量
int bulk;
//下载进程
int progress;
char cfgfile[];
char logfile[];
struct Ant* ants[];
struct Mission ms;
//响应异常退出将urlant数据结构中的变量值存放到log文件
void justpause()
{
int i;
FILE* log;
log=fopen(logfilew);
fprintf(log%s msurl);
for(i=;iamount!=)
fprintf(log %d:%d ants[i]>positionants[i]>amount);
fclose(log);
exit();
}
//总算挨到主程序了呵呵
int main(int argcchar** argv)
{
int n;
int maxfd;
char savefile[];
FILE* goods;
FILE* log;
fd_set rsetaset;
int finished;
int length;
char status[];
char c;
struct sigaction sa;
//初始化环境参数
init_env( );
//对命令行传进来的参数做判断
while((c=getopt(argcargvn:u:s:p:l:h))!=EOF){
switch (c){
//取得蚂蚁数目
case n:
ant_num=atoi(optarg);
if(ant_num > MAXANTNUM)
ant_num = MAXANTNUM;
break;
//取得目标的url地址
case u:
strcpy(msurl optarg);
break;
//取得代理的地址
case s:
strcpy(proxy_server optarg);
use_proxy=;
break;
//取得代理的端口
case p:
use_proxy=;
proxy_port=(u_short)atoi(optarg);
break;
//取得日志文件名
case l:
strcpy(logfileoptarg);
break;
case h:
printf(usage: ant n antnum u url s proxyserver p
prxoy_port l logfile );
return ;
}
}
//从日志文件中读取url
if(logfile[] != ){
log = fopen(logfile r+);
strcpy(msurlget_url_from_log(log));
}
//将值赋代理服务器的相关变量
if(use_proxy){
strcpy(mshostproxy_server);
msport=proxy_port;
}else{
strcpy(mshost extract_from_url(msurl SITENAME));
msport = atoi(extract_from_url(msurl PORTNAME));
}
//如果有下载日志从日志中取相关信息
if(logfile[] != ){
printf(The file you havent downloadcontinue);
n=;
strcpy(msurlget_url_from_log(log));
while () {
ants[n] = (struct Ant*)malloc(sizeof(struct Ant));
memset(ants[n] sizeof(struct Ant));
if(!(assign_mission(log ants[n])))
break;
n++;
if(n > MAXANTNUM){
printf(You logfile must be wrong! );
exit();
}
}
fclose(log);
free(ants[n]);
ant_num=n;
}
else{
//取得下载文件的大小为每只蚂蚁分配下载位置
bulk=get_size_of_url(&ms);
if(bulk==){
printf(Cannot get the size of this object! );
ant_num=;
ants[] = (struct Ant*)malloc(sizeof(struct Ant));
ants[]>position=;
ants[]>amount=;
}
else if(bulk==){
printf(Cannot connect to the site! );
exit();
}
else{
for(n=; nposition = (bulk/ant_num)*n;
if(n!=(ant_num))
ants[n]>amount = bulk/ant_num;
else
ants[n]>amount = bulk(bulk/ant_num)*(ant_num);
}
}
}
//}
maxfd=;
//重设&rset
FD_ZERO(&rset);
//下载按蚂蚁数开线程
for(n=; nants[n]>s?maxfd:ants[n]>s;
}
}
if(!maxfd){
printf(no ant go work! );
return ;
}
memset(&sasizeof(struct sigaction));
//打开存储文件
strcpy(savefile extract_from_url(msurl FILENAME));
if(!(goods=fopen(savefile r+))){
if(!(goods=fopen(savefilew))){
printf(Can not open file to save );
exit();
}
}
strcpy(logfile savefile);
strcat(logfile log);
//处理进程改变
sasa_handler=justpause;
sasa_flags=SA_ONESHOT;
sigaction(SIGINT &sa NULL);
maxfd++;
finished = ;
progress = ;
printf( );
printf(Downloading now! );
while(){
if(finished==ant_num){
break;
}
aset=rset;
select(maxfd&asetNULLNULLNULL);
for(n=;ns&aset)){
if(!(length=receive(ants[n] goods))){
unenroll(ants[n] &rset);
finished++;
}
}
}
}
unlink(logfile);
log=(FILE*)NULL;
//打开日志文件
if(ant_num!=){
for(n=;namount){
if(!log){
log=fopen(logfile w+);
fputs(msurl log);
fputc( log);
}
//保存状态
save_status(ants[n] log);
printf(Ant %d have not done!%d n+ants[n]>amount);
}
else
printf(Ant %d done! n+);
free(ants[n]);
}
}
else
free(ants[]);
fclose(goods);
if(log)
fclose(log);
return ;
}
D写完程序下面就是做makefile程序比较小所以MAKEFILE也比较简单
CC = gcc
CFLAGS =
source=anth antc funcsc
object=anto funcso
ant:$(object)
$(CC) $(object) o $@
%o:%c
$(CC) c $< o $@ $(CFLAGS)
bak:
tar czvf anttgz Makefile $(source)
rm f $(object)
OK到这总算飞到目的地了现在你只要在命令行下用make命令就可以编译了
教训
有一个错误调了很久才发现就是当fprintf(log%s msurl)这样的语句的指针变量为空时程序执行过程中就会发生Segmentation fault (core dumped)这样的错误另外由于程序没有多加判断在输入url时千万要带上//或ftp://哪位网友有兴趣可以自己修改