Chinaunix首页 | 论坛 | 博客
  • 博客访问: 2339967
  • 博文数量: 2110
  • 博客积分: 18861
  • 博客等级: 上将
  • 技术积分: 24420
  • 用 户 组: 普通用户
  • 注册时间: 2008-04-05 18:23
文章分类

全部博文(2110)

文章存档

2011年(139)

2010年(1971)

我的朋友

分类: LINUX

2010-10-28 12:54:02

 

一)可执行脚本

  可执行脚本是内核指向解释程序的一个文本文件,这个文件必须是一个可执行目标文件,如果不可执行,execve会产生错误.

  二)可执行目标文件

  可执行目标文件主要有三种格式:a.out,COFF,ELF

  1)a.out

  a.out是assembler output的缩写格式,代表汇编程序输出.

  a.out是早期UNIX系统使用的可执行文件,现在已被ELF文件格式代替,用gcc编译出的a.out也只是一个可执行文件,而不再是文件格式.

  用file a.out或od -c a.out|head或者readelf -h a.out来确认它的文件格式确实是ELF.

  2)ECOFF

  在MIPS结构下进行编译时,内核也可以识别ECOFF格式,它是一个ELF格式出现之前的COFF(通用对象文件格式)的变体.

  同样微软的PE文件格式也是从COFF发展而来的.

  3)ELF

  ELF文件有三种类型:

  可重定位文件:也就是通常称的目标文件,后缀为.o

  共享文件:也就是通常称的库文件,后缀为.so

  可执行文件:也就是二进制可执行程序,我们所指的ELF文件正是这种类型.

  内核通过查找文件中的魔法数来识别目标文件,例如,ELF文件的标签在文件的头4个字节,分别是7F,45,4c,46

  也就是大家经常看到177,'E','L','F'.

  例如:

  readelf -h test

  ELF Header:

  Magic:   7f 45 4c 46 02 01 01 00 00 00 00 00 00 00 00 00

  Class:                             ELF64

  Data:                              2's complement, little endian

  Version:                           1 (current)

  OS/ABI:                            UNIX - System V

  ABI Version:                       0

  Type:                              EXEC (Executable file)

  Machine:                           Advanced Micro Devices X86-64

  Version:                           0x1

  Entry point address:               0x4003e0

  Start of program headers:          64 (bytes into file)

  Start of section headers:          4304 (bytes into file)

  Flags:                             0x0

  Size of this header:               64 (bytes)

  Size of program headers:           56 (bytes)

  Number of program headers:         8

  Size of section headers:           64 (bytes)

  Number of section headers:         37

  Section header string table index: 34

  但是可重定位文件(.o文件)的前四个字节也是7F,45,4C,46

  例如:

  readelf -h test.o

  ELF Header:

  Magic:   7f 45 4c 46 02 01 01 00 00 00 00 00 00 00 00 00

  Class:                             ELF64

  Data:                              2's complement, little endian

  Version:                           1 (current)

  OS/ABI:                            UNIX - System V

  ABI Version:                       0

  Type:                              REL (Relocatable file)

  Machine:                           Advanced Micro Devices X86-64

  Version:                           0x1

  Entry point address:               0x0

  Start of program headers:          0 (bytes into file)

  Start of section headers:          288 (bytes into file)

  Flags:                             0x0

  Size of this header:               64 (bytes)

  Size of program headers:           0 (bytes)

  Number of program headers:         0

  Size of section headers:           64 (bytes)

  Number of section headers:         13

  Section header string table index: 10

 

  同样的共享文件(.so)的前四个字节也是7F,45,4C,46

  readelf -h libtest.so

  ELF Header:

  Magic:   7f 45 4c 46 02 01 01 00 00 00 00 00 00 00 00 00

  Class:                             ELF64

  Data:                              2's complement, little endian

  Version:                           1 (current)

  OS/ABI:                            UNIX - System V

  ABI Version:                       0

  Type:                              DYN (Shared object file)

  Machine:                           Advanced Micro Devices X86-64

  Version:                           0x1

  Entry point address:               0x490

  Start of program headers:          64 (bytes into file)

  Start of section headers:          3560 (bytes into file)

  Flags:                             0x0

  Size of this header:               64 (bytes)

  Size of program headers:           56 (bytes)

  Number of program headers:         5

  Size of section headers:           64 (bytes)

  Number of section headers:         33

  Section header string table index: 30

  如何来区别ELF文件是否是可执行呢?答案是除了检查魔术号以外还要检查ELF文件头以确定它是可执行的文件.

  在上面的例子中,只要观察Type:即可,Type为EXEC (Executable file),即为可执行的ELF二进制程序.

  三)杂项文件

  这里所指的杂项文件为Windows程序的二进制文件,或是JAVA二进制文件.

  我们通过配置BINFMT_MISC选项来扩展execve处理这种二进制文件.

  BINFMT_MISC在内核构件中指定,它允许超级用户定义帮助应用程序,以使execve可以调用这些帮助应用程序来运行程序,所以应用程序调用execve时不需要知道将要执行的程序是否是内部linux文件.

  首先需要挂载一个专门的procfs入口

  mount binfmt_misc -t binfmt_misc /proc/sys/fs/binfmt_misc/

  ls -l

  total 0

  --w------- 1 root root 0 2010-09-20 11:01 register

  -rw-r--r-- 1 root root 0 2010-09-20 11:01 status

  其中register伪文件是为了向内核写入新规则.

  而status入口允许启用和禁用内核处理杂项文件,其中status默认为enable,表示启用内核处理杂项文件

  向register伪文件写入一个专门格式化的字符串,就可以添加新规则.格式中的多个字符由冒号隔开,如下:

  :name:type:offset:magic:mask:interpreter:flags

  解析:

  name域是任意的名称,它会在binfmt_misc目录下显示.

  type域指识别类型(M表示魔数,E表示扩展).

  offset:可选的,魔数在文件中的起始偏移量.

  magic:以魔数或者以扩展名匹配的字节序列.

  mask:用来屏蔽掉string中的一些位的字符串.

  interpreter:程序解释器的完整路径名.

  flags:可选标志,控制必须怎样调用解释程序.

  例如加入如下的规则:

  echo ':Windows:M::MZ::/usr/bin/wine:' > /proc/sys/fs/binfmt_misc/register

  加入新规则后,查看新binfmt_misc目录

  ls -l /proc/sys/fs/binfmt_misc/

  total 0

  --w------- 1 root root 0 2010-09-20 17:40 register

  -rw-r--r-- 1 root root 0 2010-09-20 11:01 status

  -rw-r--r-- 1 root root 0 2010-09-20 17:40 Windows

  查看Windows规则

  more /proc/sys/fs/binfmt_misc/Windows

  enabled

  interpreter /usr/bin/wine

  flags:

  offset 0

  magic 4d5a

  禁用该规则,向文件写入-1即可删除它,例如:

  echo -1 > /proc/sys/fs/binfmt_misc/Windows

  此时Windows文件已经不在了,查看该目录,如下:

  ls -l /proc/sys/fs/binfmt_misc/

  total 0

  --w------- 1 root root 0 2010-09-20 17:40 register

  -rw-r--r-- 1 root root 0 2010-09-20 11:01 status

阅读(358) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~