免费注册 查看新帖 |

Chinaunix

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

[FreeBSD] freebsd9.2-在ABI层对execve系统调用实现的支持-创建elf_brand_list数组 [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2014-06-26 15:20 |只看该作者 |倒序浏览
本帖最后由 71v5 于 2014-06-26 15:20 编辑

[__ElfN(Brandinfo)类型的数据对象]:
__ElfN(Brandinfo)数据对象使得freebsd可以不加修改的执行在其它os上编译好的elf可执行文件
(比如linux,前提是底层硬件平台要一致),如果想要在freebsd上执行一个在其他操作系统上已经编
译好的elf可执行文件,那么freebsd内核中都要为相应的操作系统定义其对应的Elf32_Brandinfo数据对象,
并且在内核初始化阶段将其添加到elf_brand_list数组中,在解析elf可执行文件的过程中,函数
__elfN(get_brandinfo)会根据elf文件中包含的信息在数组elf_brand_list中选择一个最合适的
Elf32_Brandinfo对象。
  1. /*********************************************************************************************
  2. * 成员描述:
  3.    brand:
  4.    Operating system / ABI identification,在不同的操作系统上编译一个c文件后,elf可执行
  5.    文件头部都有相应的标识符来标识该c文件具体是在哪种操作系统上编译的,elf可执行文件头
  6.    部的这个标识符就和brand成员想对应,常见取值如下:
  7.    #define        ELFOSABI_LINUX                3        GNU/Linux
  8.    #define        ELFOSABI_FREEBSD        9        FreeBSD。

  9.    machine:
  10.    标识了底层的硬件cpu平台,在elf可执行文件头部也有其对应的成员,常见值如下:
  11.    #define        EM_386                3        Intel i386.
  12.    #define        EM_ARM                40        ARM.
  13.    
  14.    compat_3_brand:
  15.    一个字符串,__elfN(get_brandinfo)函数在选择适用该elf可执行文件的__ElfN(Brandinfo)
  16.    对象时使用。

  17.    emul_path,interp_path,interp_newpath:
  18.    指向三个解释器的路径名字符串,这里的解释器不是类似shell,python等这样的解释器,
  19.    这里的解释器负责对elf可执行文件中未解决的符号引用进行解析,即用实际有意义的值替换
  20.    这些符号,典型就是c程序使用了函数库中的相关函数。

  21.    在elf可执行文件中,类型为PT_INTERP的程序段中也包含一个解释器的路径名字符串,这个
  22.    解释器一般情况下和interp_path成员指向的解释器相同。

  23.    emul_path:如果该成员非空,那么emul_path指向的字符串作为解释器路径名的一部分。
  24.    interp_path:指向一个有意义的解释器字符串。
  25.    interp_newpath:如果该成员非空,首先使用该解释器。

  26.    

  27.    flags:一些标志。

  28.    brand_note:只有elf可执行文件包含类型为PT_NOTE的程序段时,该成员的值才有意义,
  29.                这里忽略。

  30.    sysvec:最最重要的成员,指向的数据对象类型为struct sysentvec,该数据对象包含了
  31.            内核实现系统调用的方法表,以及从系统调用获取参数的方法,在系统调用返回
  32.            时进行相应处理的方法。假如在linux系统上编译了一个c代码,改代码执行了
  33.            一个read系统调用,在linux系统上编译后得到的elf可执行文件依然可以在freebsd
  34.            上不加修改的执行,只要正确设置了struct proc对象的sysvec成员(该成员正是
  35.            这里的sysvec成员),再加上上面描述的解释器的帮助,那么就可以正确的运行。
  36.            这里说的比较抽象,后续在分享系统调用陷入机制的过程中会以一个实例来说明,
  37.            这样就一目了然了。
  38. *********************************************/
  39.     67        typedef struct {
  40.     68                int brand;
  41.     69                int machine;
  42.     70                const char *compat_3_brand;        /* pre Binutils 2.10 method (FBSD 3) */
  43.     71                const char *emul_path;
  44.     72                const char *interp_path;
  45.     73                struct sysentvec *sysvec;
  46.     74                const char *interp_newpath;
  47.     75                int flags;
  48.     76                Elf_Brandnote *brand_note;
  49.     77        #define        BI_CAN_EXEC_DYN                0x0001
  50.     78        #define        BI_BRAND_NOTE                0x0002        /* May have note.ABI-tag section. */
  51.     79        #define        BI_BRAND_NOTE_MANDATORY        0x0004        /* Must have note.ABI-tag section. */
  52.     80        } __ElfN(Brandinfo);
复制代码
下面列出内核中定义的几个比较典型的Elf32_Brandinfo数据对象:
[支持在freebsd上编译好的elf可执行文件]:
  1.     87        static Elf32_Brandinfo freebsd_brand_info = {
  2.     88                .brand                = ELFOSABI_FREEBSD,
  3.     89                .machine        = EM_386,
  4.     90                .compat_3_brand        = "FreeBSD",
  5.     91                .emul_path        = NULL,
  6.     92                .interp_path        = "/libexec/ld-elf.so.1",
  7.     93                .sysvec                = &elf32_freebsd_sysvec,
  8.     94                .interp_newpath        = NULL,
  9.     95                .brand_note        = &elf32_freebsd_brandnote,
  10.     96                .flags                = BI_CAN_EXEC_DYN | BI_BRAND_NOTE
  11.     97        };
复制代码
[用来支持在linux上编译好的elf可执行文件]:
  1.   1083        static Elf32_Brandinfo linux_glibc2brand = {
  2.   1084                .brand                = ELFOSABI_LINUX,
  3.   1085                .machine        = EM_386,
  4.   1086                .compat_3_brand        = "Linux",
  5.   1087                .emul_path        = "/compat/linux",
  6.   1088                .interp_path        = "/lib/ld-linux.so.2",
  7.   1089                .sysvec                = &elf_linux_sysvec,
  8.   1090                .interp_newpath        = NULL,
  9.   1091                .brand_note        = &linux_brandnote,
  10.   1092                .flags                = BI_CAN_EXEC_DYN | BI_BRAND_NOTE
  11.   1093        };
复制代码
Elf32_Brandinfo类型的数据对象最后都通过函数elf32_insert_brand_entry添加到elf_brand_list数组中:
  1. /***************************************************************************
  2. * #define OLD_EI_BRAND    8
  3.    static Elf_Brandinfo *elf_brand_list[MAX_BRANDS];
  4.   
  5.    __elfN(insert_brand_entry)函数作用一目了然,再次假设数组elf_brand_list
  6.    初始化后取值如下:
  7.    elf_brand_list[0] = &freebsd_brand_info;
  8.    elf_brand_list[1] = &linux_glibc2brand;
  9. **********************************/
  10.    206        int
  11.    207        __elfN(insert_brand_entry)(Elf_Brandinfo *entry)
  12.    208        {
  13.    209                int i;
  14.    210       
  15.    211                for (i = 0; i < MAX_BRANDS; i++) {
  16.    212                        if (elf_brand_list[i] == NULL) {
  17.    213                                elf_brand_list[i] = entry;
  18.    214                                break;
  19.    215                        }
  20.    216                }
  21.    217                if (i == MAX_BRANDS) {
  22.    218                        printf("WARNING: %s: could not insert brandinfo entry: %p\n",
  23.    219                                __func__, entry);
  24.    220                        return (-1);
  25.    221                }
  26.    222                return (0);
  27.    223        }
复制代码
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

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

清除 Cookies - ChinaUnix - Archiver - WAP - TOP