Docker で "no such file or directory" が出たときの対処法

1pt   2018-07-12 06:34
IT技術情報局

適当なプログラムをコンパイルして

$ docker run -it --rm -v $PWD:/go/src/github.com/bgpat/helloworld-server golang bash root@7dedc18b6923:/go# cd src/github.com/bgpat/helloworld-server/ root@7dedc18b6923:/go/src/github.com/bgpat/helloworld-server# go build -o bin/helloworld root@7dedc18b6923:/go/src/github.com/bgpat/helloworld-server# exit

実行すると “no such file or directory” が出るけど

$ docker run -it --rm -v $PWD/bin:/usr/local/bin alpine helloworld standard_init_linux.go:190: exec user process caused "no such file or directory"

ファイルはある

$ docker run -it --rm -v $PWD/bin:/usr/local/bin alpine which helloworld /usr/local/bin/helloworld $ docker run -it --rm -v $PWD/bin:/usr/local/bin alpine ls -al /usr/local/bin/helloworld -rwxr-xr-x 1 root root 6617238 Jul 11 16:39 /usr/local/bin/helloworld

というときの対処法。

原因

dynamic link されたライブラリが見つからないのが原因。

Docker では Alpine Linux などの軽いイメージが用いることが多いが、
イメージサイズを削るために一般的なライブラリが入っていなかったり、
互換ライブラリ使っていたりするのでこのようなエラーが出る。

対処法1

static link すれば実行時に必要なライブラリがないので動く。

$ docker run -it --rm -v $PWD:/go/src/github.com/bgpat/helloworld-server golang bash root@5e7fa9b09bfa:/go# cd src/github.com/bgpat/helloworld-server/ root@5e7fa9b09bfa:/go/src/github.com/bgpat/helloworld-server# go build --ldflags '-linkmode external -extldflags -static' -tags netgo -o bin/helloworld

対処法2

すでにビルドされたバイナリを使いたい場合はライブラリを揃えるしかない。
readelf コマンドを使うと必要なライブラリが見れる。

/ # readelf -l /usr/local/bin/helloworld Elf file type is EXEC (Executable file) Entry point 0x456fe0 There are 10 program headers, starting at offset 64 Program Headers: Type Offset VirtAddr PhysAddr FileSiz MemSiz Flags Align PHDR 0x0000000000000040 0x0000000000400040 0x0000000000400040 0x0000000000000230 0x0000000000000230 R 0x1000 INTERP 0x0000000000000fe4 0x0000000000400fe4 0x0000000000400fe4 0x000000000000001c 0x000000000000001c R 0x1 [Requesting program interpreter: /lib64/ld-linux-x86-64.so.2] NOTE 0x0000000000000f80 0x0000000000400f80 0x0000000000400f80 0x0000000000000064 0x0000000000000064 R 0x4 LOAD 0x0000000000000000 0x0000000000400000 0x0000000000400000 0x000000000020c9b0 0x000000000020c9b0 R E 0x1000 LOAD 0x000000000020d000 0x000000000060d000 0x000000000060d000 0x00000000001c5207 0x00000000001c5207 R 0x1000 LOAD 0x00000000003d3000 0x00000000007d3000 0x00000000007d3000 0x0000000000035720 0x00000000000575b8 RW 0x1000 DYNAMIC 0x00000000003d3120 0x00000000007d3120 0x00000000007d3120 0x0000000000000130 0x0000000000000130 RW 0x8 TLS 0x0000000000000000 0x0000000000000000 0x0000000000000000 0x0000000000000000 0x0000000000000008 R 0x8 GNU_STACK 0x0000000000000000 0x0000000000000000 0x0000000000000000 0x0000000000000000 0x0000000000000000 RW 0x8 LOOS+0x5041580 0x0000000000000000 0x0000000000000000 0x0000000000000000 0x0000000000000000 0x0000000000000000 0x8 Section to Segment mapping: Segment Sections... 00 01 .interp 02 .note.go.buildid 03 .text .plt .interp .note.go.buildid 04 .rodata .rela .rela.plt .gnu.version .gnu.version_r .hash .dynstr .dynsym .typelink .itablink .gosymtab .gopclntab 05 .got.plt .dynamic .got .noptrdata .data .bss .noptrbss 06 .dynamic 07 .tbss 08 09

/lib64/ld-linux-x86-64.so.2 が必要らしい。

パッケージを検索して

https://pkgs.alpinelinux.org/contents?file=ld-linux-x86-64.so.2&path=&name=&branch=edge
68747470733a2f2f71696974612d696d6167652d

libc6-compat を入れればいいことがわかった。

/ # apk add -U libc6-compat fetch http://dl-cdn.alpinelinux.org/alpine/v3.8/main/x86_64/APKINDEX.tar.gz fetch http://dl-cdn.alpinelinux.org/alpine/v3.8/community/x86_64/APKINDEX.tar.gz (1/1) Installing libc6-compat (1.1.19-r10) OK: 15 MiB in 15 packages / # helloworld

無事起動できた!!

Source: Dockerタグが付けられた新着投稿

   ITアンテナトップページへ
情報処理/ITの話題が沢山。