免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
最近访问板块 发新帖
查看: 1004 | 回复: 0
打印 上一主题 下一主题

从源代码编译和安装程序 [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2007-04-30 18:06 |只看该作者 |倒序浏览
    从源代码编译和安装程序。
A:如何得到源代码
       什么是源代码?就是你用C语言编辑的XXX.c文件。
       从网络上下载的开源软件一般的格式是.tar.gz.
       .gz表示一种压缩方式,.tar表示一种归档方式,下面你可以看到源代码是被如何归档和压缩的,我们用rarlinux-3.6.0.tar.gz来做例子
       那么如何从这样的归档文件中找到源代码呢
       gzip -d rarlinux-3.6.0.tar.gz       -d选项表示解压缩
       我们可以看到rarlinux-3.6.0.tar.gz变成了rarlinux-3.6.0.tar.
       tar -xf rarlinux-3.6.0.tar                -xf表示把所有的文件从归档文件中释放出来
       当然,这个例子解压缩出来的并不是C的源代码,我没有找到合适的例子。
B:关于make运作方式
       我们在刚才的基础上,进入rar文件,并且运行
       make > info.txt
       看看我们的make都干了些什么?
       cat info.txt
       mkdir -p /usr/local/bin                                                     -p表示需要时创建上级目录,目录存在的时候不做错误处理。
       mkdir -p /usr/local/lib
       cp rar unrar /usr/local/bin
       cp rarfiles.lst /etc
       cp default.sfx /usr/local/lib
       再看看,rar文件夹中makfile中都有些什么?
       cat Makefile
        PREFIX=/usr/local                                                        这是shell变量,你可以用echo $PREFIX看看。
        install:
        mkdir -p $(PREFIX)/bin
        mkdir -p $(PREFIX)/lib
        cp rar unrar $(PREFIX)/bin
        cp rarfiles.lst /etc
        cp default.sfx $(PREFIX)/lib   
       很像吧,没错,因为make是按照一定的规则去完成配置文件中的内容。这个配置文件默认的名字是makefile,当然也可以变。这个配置文件对于我来说不需要会写,但是总要读的懂。
        了解下make命令的基本参数:偶不是编程的,捡有用的说。
         -c dir 这个是make工作的路径,默认是当然路径。
         -f filename 这个用指定的文件作为配置文件,默认是makefile。
         -d 打印debug信息
         在这个例子中我们可以知道make的工作方式,这对于从源代码运行程序是很有用的。
A:介绍一下可以用来搞定安装的全部工具。
       gcc-这个是编译器
       make-包含从makefiles产生二进制文件的make命令,当然还有其他的一些功能。
       glibc-重要的共享库,c库和基本的数学库。没有这个连系统都没有办法运行。
       glibc-devel-包含了创建可执行文件所需要的标准头文件。
       binutils-包含编译程序需要的使用工具,主要是汇编和链接程序。
       kernel-source-包含内核源代码
       libc-包含libc5,而上面我们提到的glibc是linc6.
       对于只想安装别人做好的软件的人,关键是gcc和make ,而其他的看看rpm中有没有就可以了。
B:关于软件包。
       linux下你可以发现的软件包,会有不同的格式,这很讨厌,但是他可以让你知道,这些开源项目是在什么环境开发和编译出来的,支持什么。
       搜集一下
       filename-4.2.3.i386.rpm                                       这个表示可以用rpm来安装,我们最喜欢的方式。
       filename-4.2.3.tar.gz                                             这个表示用gz压缩,用tar归档,至于是什么,那就不知道了
       filename-4.2.3.src.tar.gz                                      这个表示用gz压缩,用tar归档,内容是源代码   
       filename-4.2.3.bin.SPARC.tar.gz                     这个是表示用gz压缩,用tar归档,可以在SPARC工作站上运行,的2进制代码。
       filename-4.2.3.bin.ELF.static.tar.gz                 这个表示用gz压缩,用tar归档,由静态连接的FLF的可执行文件组成的2进制文件。
       4.2.3 表示第4版,第2个补丁,第3次修改。
       全面的说一下。
       rpm.有这个后缀表示是fedora使用的2进制文件,这个不是说里面的内容2进制的,而是说他可以被fedora的软件管理器使用。可以用归档文件管理器把他打开。
       tar.这个是用tar归档,使用tar 命令打开
       gz.和z.这个是说用gzip压缩的,用gzip命令打开
       tgz.这个扩展名和以上的结合,容易搞定
       bz2.用bzip2压缩的,可以用bip2命令打开
       taz.和tz.这个表示用tar压缩,也用tar命令打开
       lsm.这个通常是介绍归档内容的文本,可以和软件包一起下载。
       deb.这个同rpm但是用于Debian
       如果你不能肯定格式的话,可以用file命令来确定.
       好了,现在你可以把源文件从任何软包中掏出来,下面我们要编译他。
C:现在我们看一下C 的编译过程..
       预编译,编译生成汇编,汇编生成目标文件,目标文件连接库文件生成可执行文件,这个过程人人都知道,但是究竟如何呢?
       牢骚一下:太多的编译器都是一步到位,其实这对学习不是什么好事情,至少我觉得,在学习过程中把简单的东西弄的麻烦,在工作的过程中把麻烦的东西弄的简单。
       这里的例子选自 lorne
       预编译 gcc -E
        编译 gcc -S    这两个有gcc rpm包就可以。
        汇编as         
       连接ld           这两个需要安装binutils rpm包
       1,预编译
        编写c源程序game.c
        #include
          int main()
         {
           printf("Hello World!\n");
         }                   传说中的helloworld
        gcc -E -o pregame game.c
        这是会出现一个pregame文件
        看看他是什么格式
        file pregame
        pregame: ASCII C program text
        也就说预编译之后的文件仍然是c源代码。那么预编译作了些什么呢?
        可以看看都有些什么玩意.
        cat pregame
        你会发现 pregame和game 差不多,区别是pregame中没有了#include也灭有类似的格式。
        这就是预编译的作用他把game.c中包含的头文件加在main函数的上面.
        gcc -o game game.c                        生成 可执行程序 game                          
        gcc -o pregame pregame.c        生成可执行程序pregame
        注意:这两个命令,我们忽略了as和ld的步骤。
        pregame最好用.c做为文件名
        发现 game和pregame的运行结果一样,这也说明了预编译的作用.
        总结一下预编译的作用:(这些是lorne大人总结的,与我无关)
  • 把"include"的文件拷贝到要编译的源文件中。   
  • 用实际值替代"define"的文本。
  • 在调用宏的地方进行宏替换。
            2.编译。
            这个过程是用于生成汇编语言。这是编译过程的一步,是一步,是一步啊,同志们~~~~~~~~~~~~~~!!
            gcc -S -o aspregame pregame.c
            会声称一个aspregame文件,看看是什么东西?
            file aspregame
            aspregame: ASCII assembler program text
            嘿嘿出现了,汇编程序文本.
            有兴趣你可以看一下
            cat aspregame
                    .file   "pregame.c"
            .section        .rodata
    .LC0:
            .string "Hello World!"
            .text
    .globl main
            .type   main, @function
    main:
            leal    4(%esp), %ecx
            andl    $-16, %esp
            pushl   -4(%ecx)
            pushl   %ebp
            movl    %esp, %ebp
            pushl   %ecx
            subl    $4, %esp
            movl    $.LC0, (%esp)
            call    puts
            addl    $4, %esp
            popl    %ecx
            popl    %ebp
            leal    -4(%ecx), %esp
            ret
            .size   main, .-main
            .ident  "GCC: (GNU) 4.1.0 20060304 (Red Hat 4.1.0-3)"
            .section        .note.GNU-stack,"",@progbits
    传说中的汇编。
            最好用.asm作为文件名。
            3.生成目标文件.
              这一步我们可以用gcc来完成,但是还是用as吧,总觉得一步到位的东西,不是很适合学习。
              as -o ldaspregame aspregame
              会生成ldaspregame文件
              看看他是什么?
              file ldaspregame
              ldaspregame: ELF 32-bit LSB relocatable, Intel 80386, version 1 (SYSV), not stripped
               ELF格式的文件,浮动的,意思是这个程序的地址是可以被修改来适应初始地址,其实就是未连接的目标文件。
               注意:我们可以把任何的一个.c文件通过gcc -S变成汇编,在把他变成目标文件。
              最要用.o做为文件名
            4.连接成为可执行文件
               那么现在我们来生成可执行文件吧
               这里要说明什么是动态链接库,相当于winxxx中的dll文件,在这里是so文件,ELF格式就是支持动态链接库的。
               gcc -o exldaspregame ldaspregame
               好了声称了可执行文件ldaspregame
               任何一个.c文件都可以生成目标文件,他们需要被连接来执行。
               这里我有一个问题,希望高手可以解答:
               本来我想用ld来连接文件,ld  ldaspregame
               但是提示错误为:
               ld: warning: cannot find entry symbol _start; defaulting to 08048094            对‘puts’未定义的引用
               以为是没有设置要连接的库文件。
               ld /bin/libc.so.6 ldaspregame
                仍然错误
                提示错误为
                ld: warning: cannot find entry symbol _start; defaulting to 08048094
                 entry symbol_start究竟是什么东西?gcc又是怎样完成这一步骤的?
    D:编译器稍微高级的使用方法。
                 首先,介绍模块化编程方法。
                 其实就是把程序的源代码分成多个文件。大多数的自由软件也都是这样组成的。c语言中带有main函数的文件被成为主模块,其他的是辅助模块.
                 来个例子,这个例子取自 Bradley L.Jones  PeterAitken
                 建立list2101.c,calc.c,calc.h文件.内容分别是。
                 list2101.c
                  #include
                  #include "calc.h"
                  int main(void)
                  {
                            int x;
                            printf("enter an integer value:");
                            scanf("%d",&x);
                            printf("\nthe square of %d is %ld.\n",x,sqr(x));
                            return 0;
                   }
                   calc.c
                  #include "calc.h"
                  long sqr(int x)
                  {
                            return ((long)x*x);
                   }
                    calc.h               
                   long sqr(int x);
                    未完 ......................................
              
              
             
                   
                   
                   

    本文来自ChinaUnix博客,如果查看原文请点:http://blog.chinaunix.net/u1/36086/showart_289911.html
  • 您需要登录后才可以回帖 登录 | 注册

    本版积分规则 发表回复

      

    北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
    未成年举报专区
    中国互联网协会会员  联系我们:huangweiwei@itpub.net
    感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

    清除 Cookies - ChinaUnix - Archiver - WAP - TOP