19

我认识的人在运行“ lmutil”时遇到了问题,所以我要求他们这样做strace -f lmutil。为什么execve“没有这样的文件”失败!!!这是没有意义的,因为我正在跟踪同一个文件!这里到底发生了什么???

strace -f /home/tabitha/Starprogram/FLEXlm_11.7/linux-x86_64-2.3.4/bin/lmutil

输出:

execve("/home/tabitha/Starprogram/FLEXlm_11.7/linux-x86_64-2.3.4/bin/lmutil", ["/home/tabitha/Starprogram/FLEXlm"...], [/* 38 vars */]) = -1 ENOENT (No such file or directory)
dup(2)                                  = 3
fcntl(3, F_GETFL)                       = 0x8002 (flags O_RDWR|O_LARGEFILE)
fstat(3, {st_mode=S_IFCHR|0620, st_rdev=makedev(136, 1), ...}) = 0
mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7fd7cb8b0000
lseek(3, 0, SEEK_CUR)                   = -1 ESPIPE (Illegal seek)
write(3, "strace: exec: No such file or di"..., 40strace: exec: No such file or directory
) = 40
close(3)                                = 0
munmap(0x7fd7cb8b0000, 4096)            = 0
exit_group(1)                           = ?

ldd 输出

$ ldd ./lmutil
        linux-vdso.so.1 => (0x00007fffcd5ff000)
        libpthread.so.0 => /lib/libpthread.so.0 (0x00007fe40ebbe000)
        libm.so.6 => /lib/libm.so.6 (0x00007fe40e93b000)
        libgcc_s.so.1 => /lib/libgcc_s.so.1 (0x00007fe40e724000)
        libc.so.6 => /lib/libc.so.6 (0x00007fe40e3a1000)
        libdl.so.2 => /lib/libdl.so.2 (0x00007fe40e19d000)
        /lib64/ld-lsb-x86-64.so.3 => /lib64/ld-linux-x86-64.so.2 (0x00007fe40edf5000)
$查找。-name lmutil -exec 文件 {} \;
./bin.linux.x86_64/lmutil:ELF 64 位 LSB 可执行文件,AMD x86-64,版本 1 (SYSV),适用于 GNU/Linux 2.4.0,动态链接(使用共享库),适用于 GNU/Linux 2.4。 0,剥离
./bin.linux.x86/lmutil:ELF 32 位 LSB 可执行文件,Intel 80386,版本 1 (SYSV),适用于 GNU/Linux 2.2.5,动态链接(使用共享库),适用于 GNU/Linux 2.2.5,剥离
./lmutil:Bourne shell 脚本文本可执行文件
4

5 回答 5

18

您尝试执行的文件 ( …/lmutil) 存在,但它的“加载程序”不存在,其中

  • 本机可执行文件的加载器是它的动态加载器,例如/lib/ld-linux.so.2
  • 脚本的加载程序是在其 shebang 行中提到的程序,例如,/bin/sh如果脚本以#!/bin/sh.

从目录的名称来看,很有可能lmutil是一个 amd64 Linux 二进制文件,正在寻找/lib64/ld-linux-x86-64.so.2它的加载程序,但是您有一个运行 386(即 32 位)用户空间的 amd64 Linux 内核。您需要为您的平台获取合适的二进制文件。

我认为这种情况是 Unix 最具误导性的错误信息。不幸的是,修复它会很困难:内核只能向程序的调用者报告一个数字错误代码,所以它只有“找不到命令”(ENOENT)的空间,而不是它正在寻找的加载程序的名称。strace这是这些无济于事的罕见情况之一。

于 2011-03-08T23:20:21.937 回答
6

您的 ldd 输出指的是 /lib64/ld-lsb-x86-64.so.3,但除非(在 Ubuntu 上)您已安装 lsb-core 软件包,否则此加载程序可能实际上并不存在。包的 postinst 脚本在 /lib* 目录中创建相关的符号链接。

于 2011-04-14T14:28:52.100 回答
3

只是一点猜测,但我的第一个问题是遇到此问题的用户是否可以在没有 strace 的情况下自行运行可执行文件。

execve 手册页还说,如果找不到文件或所需的脚本解释器或共享库,则会发生 ENOENT。(我注意到这里涉及 64 位。是否所有正确的库都可用?)

该文件是本机可执行文件还是某种脚本?

这看起来像一个许可管理器——它有没有故意让自己难以调试?

说到用户,“tabitha”是可执行文件所在的目录中的用户有问题吗?或者我们是否正在考虑尝试运行由另一个普通用户安装的程序而不是以 root 用户以正常的系统范围方式安装的程序的可能复杂性?

于 2011-03-08T17:33:43.463 回答
2

您可以使用readelf(任何 readelf 都应该这样做,您不需要来自特殊交叉编译器工具链的工具链)来检查动态加载或可执行文件需要哪个加载器。

$ readelf -l <filename> |grep -i interp
...
[Requesting program interpreter: /system/bin/linker]
于 2014-11-03T08:51:21.990 回答
0

execve 手册页

成功时, execve() 不返回,错误时返回 -1,并适当设置 errno。

strace假设这-1意味着“找不到文件”,因为errnoENOENT-1并且strace没有区别。

那么,本质上,您可以忽略这一点:这-1只是意味着发生了一些错误。strace输出没有告诉你的价值是什么errno

我将其写为警告调用,不要急于得出结论strace并返回值,即使结果可能errno仍然ENOENT存在

于 2011-03-08T15:02:06.290 回答