standard_init_linux.go:211:exec 用户进程在 alpine linux 和 python 中导致“没有这样的文件或目录”

Dan*_*gel 2 python docker dockerpy alpine-linux

我有一个包含 docker 文件、attack.py 和 requirements.txt 的目录。

使用它,我创建了以下 dockerfile:

FROM arm64v8/python:3.7-alpine

COPY qemu-arm-static /usr/bin

COPY ./ app-ids
WORKDIR /app-ids

RUN pip install --no-cache-dir -r requirements.txt

CMD["python","./attack.py"]
Run Code Online (Sandbox Code Playgroud)

但是,pip install 行抛出:standard_init_linux.go:211:exec user process 导致“没有这样的文件或目录”

我不明白为什么。使用 ls、pwd 等命令尝试调试会产生相同的错误。

谁能解释一下我到底做错了什么?

ait*_*rhh 7

我猜您正在尝试在非 arm64v8 平台上构建 docker 映像。对于其余的答案,我会假设。

提供的解决方案将特定于 Ubuntu 发行版(主机),但我想它在其他 linux 发行版上应该是类似的。

解决方案 1 [在 Ubuntu 18.04 上工作]

https://github.com/docker/for-linux/issues/56我们可以看到目前 Debian(以及 Ubuntu?)的软件包中存在错误。

sudo apt-get install qemu-user-static

git clone https://github.com/computermouth/qemu-static-conf.git
sudo mkdir -p /lib/binfmt.d
sudo cp qemu-static-conf/*.conf /lib/binfmt.d/
sudo systemctl restart systemd-binfmt.service
Run Code Online (Sandbox Code Playgroud)

qemu-user-binfmt将从解决方案 2 中删除该方法。但是,在该包中,提供的配置文件不在文件夹中,并且配置错误,供systemd-binfmt.

此外,我们从 git 存储库中获取配置文件,并将它们放在 systemd-binfmt 查看的文件夹中:(/lib/binfmt.d/不是/var/lib/binfmts/qemu-user-static 安装的)

然后检查状态:

systemctl status systemd-binfmt
Run Code Online (Sandbox Code Playgroud)

并尝试再次编译您的 docker。它应该工作!

解决方案 2 [目前不在 Ubuntu 18.04 上工作]

以前它是手动配置过程,但现在通过 apt 包支持:

sudo apt-get install qemu-user-binfmt
Run Code Online (Sandbox Code Playgroud)

有了它,它将binfmt/proc/sys/fs/binfmt_misc/qemu-*. 并且当您的系统检测到可执行文件是针对 arm 的时,它会调用 qemu 而不是尝试直接执行。

这是更详细解释的链接:https : //ownyourbits.com/2018/06/13/transparently-running-binaries-from-any-architecture-in-linux-with-qemu-and-binfmt_misc/https ://ownyourbits.com/2018/06/27/running-and-building-arm-docker-containers-in-x86/

要了解它是如何工作的,最好阅读以下段落:

内核识别 ARM ELF 魔法,并使用解释器 /usr/bin/qemu-arm-static,这是架构的正确 QEMU 二进制文件。0x7F 'ELF' 十六进制是7f 45 4c 46,所以我们可以看到魔法和掩码是如何一起工作的,考虑到 ELF 头的结构

typedef struct {
    unsigned char e_ident[EI_NIDENT];   /* 0x7F 'ELF' four byte ELF magic for any architecture */
    uint16_t e_type;
    uint16_t e_machine;                 /* architecture code, 40=0x28 in the case of ARM */
    uint32_t e_version;
    ElfN_Addr e_entry;
    ElfN_Off e_phoff;
    ElfN_Off e_shoff;
    uint32_t e_flags;
    uint16_t e_ehsize;
    uint16_t e_phentsize;
    uint16_t e_phnum;
    uint16_t e_shentsize;
    uint16_t e_shnum;
    uint16_t e_shstrndx;
} ElfN_Ehdr;
Run Code Online (Sandbox Code Playgroud)

请注意,binfmt配置由 docker 共享,因此它将尝试获取/usr/bin/qemu-arm-static容器内部。这就是您仍然需要复制 /usr/bin/qemu-arm-static 的原因。