Docker Alpine 和 perf 在 docker 容器中相处不来

Docker Alpine and perf not getting along in docker container

要事第一:

  1. Alpine 版本 3.9.0
  2. 性能[来自:http://dl-cdn.alpinelinux.org/alpine/edge/testing] 4.18.13
  3. Docker 18.09.3 构建 774a1f4

我的Docker文件

FROM alpine:latest

# Set the working directory to /app
WORKDIR /app/

# Install any needed packages specified in requirements.txt
RUN yes | apk add vim
RUN echo "http://dl-cdn.alpinelinux.org/alpine/edge/testing" | tee -a  /etc/apk/repositories
RUN apk add --update perf

问题,这些是容器内的命令运行:

/ # cat /proc/sys/kernel/perf_event_paranoid 
-1
/ # perf stat -d sleep 1
Error:
No permission to enable task-clock event.

You may not have permission to collect stats.

Consider tweaking /proc/sys/kernel/perf_event_paranoid,
which controls use of the performance events system by 
unprivileged users (without CAP_SYS_ADMIN).

The current value is -1:

   -1: Allow use of (almost) all events by all users
       Ignore mlock limit after perf_event_mlock_kb without CAP_IPC_LOCK
 >= 0: Disallow ftrace function tracepoint by users without CAP_SYS_ADMIN
       Disallow raw tracepoint access by users without CAP_SYS_ADMIN
 >= 1: Disallow CPU event access by users without CAP_SYS_ADMIN
 >= 2: Disallow kernel profiling by users without CAP_SYS_ADMIN

 To make this setting permanent, edit /etc/sysctl.conf too, e.g.:

      kernel.perf_event_paranoid = -1

 / # 

启动镜像的命令:

docker run -it --mount type=tmpfs,tmpfs-size=512M,destination=/app/ alpy

我已经使用 perf 很长时间了。但是,这是第一次。有谁知道为什么 perf 知道我有配置文件的权限,但不让我这样做?

谢谢。

问题是 Docker 默认情况下会阻止一系列系统调用,包括 perf 严重依赖的 perf_event_open。

官方 docker 参考:https://docs.docker.com/engine/security/seccomp/

解决方案:

  • 为 docker 下载标准 seccomp(安全计算)file。这是一个 json 文件。
  • 找到"perf_event_open",只出现一次,删掉
  • 在系统调用部分添加一个新条目:

    { "names": ["perf_event_open" ], "action": "SCMP_ACT_ALLOW" },

  • 将以下内容添加到 运行 容器的命令中: --security-opt seccomp=path/to/default.json

这对我有用。

只是 F.Y.I 对于那些想要 运行 perf 在 Alpine 上通过 docker-compose.

tl;博士

  • 将以下 2 个条目添加到您要使用的服务中 perf
    cap_add:
      - SYS_PTRACE
    security_opt:
      - seccomp:unconfined
  • 请注意,安全选项已设置为 unconfined,因此您必须知道自己是什么 运行ning。

ts;博士

  • Docker 文件
FROM ${BASEIMAGE}

RUN \
    apk add --no-cache perf && \
    # Smoke-test
    perf --version
  • docker-compose.yml
version: "3.9"
services:
  go:
    build:
      context: .
      dockerfile: ./Dockerfile
      args:
        BASEIMAGE: golang:alpine
    volumes:
      - .:/tmp/bench
    working_dir: /tmp/bench
    cap_add:
      - SYS_PTRACE
    security_opt:
      - seccomp:unconfined
    entrypoint: [ "perf", "stat", "-r5", "go", "run", "./fibonacci.go" ]
  python:
    build:
      context: .
      dockerfile: ./Dockerfile
      args:
        BASEIMAGE: python:3-alpine
    volumes:
      - .:/tmp/bench
    working_dir: /tmp/bench
    cap_add:
      - SYS_PTRACE
    security_opt:
      - seccomp:unconfined
    entrypoint: [ "perf", "stat", "-r5", "python", "./fibonacci.py" ]

  • Shell 会话
$ docker-compose build
** snip **

$ docker-compose run go
9227465
9227465
9227465
9227465
9227465

 Performance counter stats for 'go run ./fibonacci.go' (5 runs):

            566.09 msec task-clock:u              #    1.336 CPUs utilized            ( +-  3.43% )
                 0      context-switches:u        #    0.000 /sec                   
                 0      cpu-migrations:u          #    0.000 /sec                   
             10864      page-faults:u             #   20.656 K/sec                    ( +-  3.77% )
   <not supported>      cycles:u                                                    
   <not supported>      instructions:u                                              
   <not supported>      branches:u                                                  
   <not supported>      branch-misses:u                                             

            0.4236 +- 0.0186 seconds time elapsed  ( +-  4.40% )

$ docker-compose run python
9227465
9227465
9227465
9227465
9227465

 Performance counter stats for 'python ./fibonacci.py' (5 runs):

           4487.88 msec task-clock:u              #    0.987 CPUs utilized            ( +-  0.40% )
                 0      context-switches:u        #    0.000 /sec                   
                 0      cpu-migrations:u          #    0.000 /sec                   
               949      page-faults:u             #  209.758 /sec                     ( +- 88.64% )
   <not supported>      cycles:u                                                    
   <not supported>      instructions:u                                              
   <not supported>      branches:u                                                  
   <not supported>      branch-misses:u                                             

            4.5453 +- 0.0175 seconds time elapsed  ( +-  0.39% )

$ # Env info
$ docker --version
Docker version 20.10.11, build dea9396
$ docker-compose --version
Docker Compose version v2.2.1
$ sw_vers
ProductName:    Mac OS X
ProductVersion: 10.15.7
BuildVersion:   19H1615