beanstalk源码剖析——文件结构和启动程序

1. 文件结构组织

beanstalk的源码文件物理组织如下:

makefile文件:Makefile
数据结构定义: dat.h
主程序:      main.c
Server实例:   serv.c
协议处理:     prot.c
连接管理:     conn.c    
tube管理:     tube.c  
job管理:      job.c
集合管理:     ms.c        
daemon监听端口: net.c     
epoll抽象:      linux.c
堆操作:         heap.c
daemon框架:     sd-daemon.h  sd-daemon.c
binlog处理:     file.c walg.c
系统时间:       time.c
rehash用的质数: primes.c
辅助工具:       util.c
freebsd支持:    darwin.c freebsd.c
版本处理:       verc.sh  vers.sh
测试程序:       testjobs.c  testheap.c  testserv.c  testutil.c
文档文件:       LICENSE README

adm:系统管理工具
launchd  Readme  systemd  upstart

ct:测试工具
ct.c  ct.h  gen  internal.h  License

doc:文档
beanstalkd.1  beanstalkd.1.html  beanstalkd.ronn  protocol.md  protocol.txt

pkg:其他辅助工具
beanstalkd.spec.in  bloghead.in  dist.sh  mail.sh  newstail.in

 

2. 启动程序

启动程序和普通的命令行程序的结构一致,这一部分也可以采用第三方库。这里作者为了避免对第三方程序的依赖,采用了自己实现。

int
main(int argc, char **argv)
{
    int r;
    struct job list = {};

    progname = argv[0];
    setlinebuf(stdout);  //设置行缓冲
    optparse(&srv, argv+1);  //解析输入参数

    if (verbose) {
        printf("pid %d\n", getpid());
    }
    //绑定监听端口
    r = make_server_socket(srv.addr, srv.port);
    if (r == -1) twarnx("make_server_socket()"), exit(111);
    srv.sock.fd = r;
    //初始化协议
    prot_init();
    //切换用户,处理信号
    if (srv.user) su(srv.user);
    set_sig_handlers();
    //日志初始化移到wal.c模块会更清晰一些
    if (srv.wal.use) {
        // We want to make sure that only one beanstalkd tries
        // to use the wal directory at a time. So acquire a lock
        // now and never release it.
        if (!waldirlock(&srv.wal)) {
            twarnx("failed to lock wal dir %s", srv.wal.dir);
            exit(10);
        }

        list.prev = list.next = &list;
        walinit(&srv.wal, &list);
        r = prot_replay(&srv, &list);
        if (!r) {
            twarnx("failed to replay log");
            return 1;
        }
    }
    //启动Server实例
    srvserve(&srv);
    return 0;
}
posted @ 2013-08-24 12:32  blockcipher  阅读(511)  评论(0编辑  收藏  举报