Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Docker: Support x86_64, armv7 and aarch64 docker image #3058

Closed
3 tasks done
winlinvip opened this issue Jun 2, 2022 · 3 comments
Closed
3 tasks done

Docker: Support x86_64, armv7 and aarch64 docker image #3058

winlinvip opened this issue Jun 2, 2022 · 3 comments
Assignees
Labels
good first issue Easy to fix issues, good for newcomers help wanted Extra attention is needed TransByAI Translated by AI/GPT.
Milestone

Comments

@winlinvip
Copy link
Member

winlinvip commented Jun 2, 2022

ARM server is everywhere, SRS should support linux/amd64, linux/arm/v7 and linux/arm64/v8 image. It also enable us to run SRS on Apple M1 by docker.

Recently, I have noticed a trend, which is the increasing number of ARM servers. However, it seems that ARM is not as easily recognizable as the x64 platform, as there are always various ARM versions that cannot be identified. If SRS could provide ARM docker images, it would be easier to run.

SRS already supports docker images for multiple CPU architectures, as shown in the following image:

173718382-5dc89db3-ca0c-4880-b5d1-2b11ae5337e7

Below are the usage and technical background.

Usage

Now SRS supports multiple CPU architectures, refer to ossrs/srs:

  • linux/amd64 This is the x86_64 architecture, Intel's 64-bit server. Currently, most Linux servers are of this type, and any operating system that uses this chip can use this image. Apple Mac with Intel chips can also use this image.
  • linux/arm/v7 This is the armv7 architecture, which is a 32-bit architecture. For example, Raspberry PI uses this type of server. If you want to use SRS on a PI, you can use this image. I haven't verified it with hardware, so I welcome everyone to test and provide feedback.
  • linux/arm64/v8 This is the armv8 architecture, which is a 64-bit architecture. Currently, most ARM cloud servers use this architecture, and any operating system can use this image. Apple Mac with M1 chips should be able to use this image as well. I don't have the hardware to verify it, so I welcome everyone to test and provide feedback.

Note: In China, you can use the Alibaba Cloud image registry.cn-hangzhou.aliyuncs.com/ossrs/srs. Please note that it may not display multiple CPU architectures, but it is still supported.

The usage is the same as before. Docker will select the appropriate image based on the machine's CPU architecture. So there is no change in usage. Here is a simple example:

docker run --rm -it -p 1935:1935 -p 1985:1985 -p 8080:8080 \
    ossrs/srs:4 ./objs/srs -c conf/docker.conf

In China, you can use Alibaba Cloud mirror, for example:

docker run --rm -it -p 1935:1935 -p 1985:1985 -p 8080:8080 \
    registry.cn-hangzhou.aliyuncs.com/ossrs/srs:4 ./objs/srs -c conf/docker.conf

For more examples, you can refer to the Wiki:

Below are additional backgrounds on images that support multi-CPU architectures. If you need to modify the code and build your own image, or if you need support for other CPU architectures, you can refer to the following resources.

Note: In addition to the SRS image, the development images for SRS, CentOS 7 and Ubuntu 20, support multi-CPU architectures. Please note that CentOS does not support linux/arm/v7. For more details, please refer to the detailed description later in this document.

Verify

If you need to verify the arm/v7 architecture, you can choose RaspberryPI. Currently, cloud servers are all based on the arm64/v8 architecture.

In fact, SRS can support multiple CPUs, such as x86_64, arm, aarch64, mips, loongarch, etc. Please refer to ST: Adaptation for specific details. However, separate adaptation is required to support these CPUs in docker images.

You can choose cloud servers to verify ARM docker, such as Tencent Cloud ARM, Alibaba Cloud ARM, Huawei Cloud Kunpeng, AWS ARM.

Execute the command to view the CPU architecture of the machine:

# uname -p
aarch64

Start Docker and check the CPU architecture in the container:

docker run -it --rm ossrs/srs:ubuntu20 uname -p
aarch64

docker run -it --rm registry.cn-hangzhou.aliyuncs.com/ossrs/srs:ubuntu20 uname -p
aarch64

The development image verification is complete. Let's verify the SRS image on an ARM cloud host with a CPU architecture of aarch64, which is linux/arm64/v8. Execute the following command:

docker run --rm -it registry.cn-hangzhou.aliyuncs.com/ossrs/srs:v4 ldd objs/srs
	libdl.so.2 => /lib/aarch64-linux-gnu/libdl.so.2 (0x0000ffff97240000)
	libpthread.so.0 => /lib/aarch64-linux-gnu/libpthread.so.0 (0x0000ffff97200000)
	libstdc++.so.6 => /lib/aarch64-linux-gnu/libstdc++.so.6 (0x0000ffff97010000)
	libm.so.6 => /lib/aarch64-linux-gnu/libm.so.6 (0x0000ffff96f60000)
	libgcc_s.so.1 => /lib/aarch64-linux-gnu/libgcc_s.so.1 (0x0000ffff96f30000)
	libc.so.6 => /lib/aarch64-linux-gnu/libc.so.6 (0x0000ffff96db0000)
	/lib/ld-linux-aarch64.so.1 (0x0000ffff97c10000)

It can be seen that Docker has successfully downloaded the image for the aarch64 architecture. Verification is complete.

SRS Image

If you need to build your own multi-CPU architecture image for SRS, you can refer to the details in this section.

Note: Since the base development image ossrs/srs:ubuntu20 supports multi-CPU architecture, the compilation of the SRS image becomes relatively simple. You just need to modify it from ossrs/srs:dev to ossrs/srs:ubuntu20, and also modify the installation commands from CentOS to Ubuntu. For detailed modifications in the published image, please refer to the commit: xxxx.

To perform the operation, it is very simple. You can simply use the command to package it:

docker buildx create --name mybuilder --driver docker-container
docker buildx use mybuilder

cd ~/git/srs
docker buildx build --platform linux/arm/v7,linux/arm64/v8,linux/amd64 \
  --output "type=image,push=true" --progress plain --build-arg JOBS=10 \
  --tag your-repository/ossrs/srs:4 -f trunk/Dockerfile .

Note: Remember to modify --tag to the image of your repository.

Multiple CPU Image

Previously, the docker for SRS only supported the x86_64 architecture, so it couldn't run on ARM and other CPUs. Please refer to SRS. Actually, images can support multiple architectures, as mentioned in Manually Building Multi-CPU Architecture Images.

To understand Docker's multi-CPU architecture images, let's first try a simple image without any dependencies.

First, create a Dockerfile with the FROM statement prefixed with ARCH:

ARG ARCH
FROM ${ARCH}debian:buster-slim

RUN apt-get update \
&& apt-get install -y curl \
&& rm -rf /var/lib/apt/lists/*

ENTRYPOINT [ "curl" ]

If you are using a Mac, you need to create a builder, for example:

docker buildx create --name mybuilder --driver docker-container
docker buildx use mybuilder

Then, use docker buildx to build the image:

docker buildx build --push --platform linux/arm/v7,linux/arm64/v8,linux/amd64 \
  -t ossrs/srs:multiarch-example .

If you need to upload to another registry like Alibaba Cloud, you can run it again. Docker has caching:

docker buildx build --push --platform linux/arm/v7,linux/arm64/v8,linux/amd64 \
  -t registry.cn-hangzhou.aliyuncs.com/ossrs/srs:multiarch-example .

This way, a multi-CPU architecture image is packaged and uploaded:

# docker manifest inspect ossrs/srs:multiarch-example

{
   "manifests": [
      { "platform": { "architecture": "arm", "variant": "v7" }  },
      { "platform": { "architecture": "arm64", } },
      { "platform": { "architecture": "amd64", } }
   ]
}

This image can be seen on Docker Hub, including multiple CPU architectures.

GitHub Actions

SRS is using GitHub Actions to automatically build the image and upload it to Docker and Aliyun image repositories.

In .github/workflows/release.yml, an additional step is required to install buildx.

      # See https://github.com/crazy-max/ghaction-docker-buildx#moved-to-docker-organization
      # https://github.com/docker/setup-qemu-action
      - name: Set up QEMU
        uses: docker/setup-qemu-action@v1
      # https://github.com/docker/setup-buildx-action
      - name: Set up Docker Buildx
        uses: docker/setup-buildx-action@v1

Note: Please note that the latest version uses qemu and official docker actions, while many documents are still outdated.

Multiple Repositories

Multi-CPU architecture images cannot be directly pushed to multiple repositories using the usual method. Instead, a separate action needs to be used.

In .github/workflows/release.yml, an additional step is required to push to multiple repositories.

      - name: Login aliyun hub
        uses: docker/login-action@v1
        with:
          registry: registry.cn-hangzhou.aliyuncs.com
          username: "${{ secrets.ACR_USERNAME }}"
          password: "${{ secrets.ACR_PASSWORD }}"
      - name: Push to Aliyun registry
        uses: akhilerm/tag-push-action@v2.0.0
        with:
          src: ossrs/srs:${{ env.SRS_TAG }}
          dst: |
            registry.cn-hangzhou.aliyuncs.com/ossrs/srs:${{ env.SRS_TAG }}

Note: Since buildx involves manifest, docker tag and docker push cannot be used directly.

ARG

The parameter ARCH can only be used in the FROM statement, and it can also be used to make judgments based on the target platform after the FROM statement.

ARG ARCH
FROM ${ARCH}centos:7 as build

ARG BUILDPLATFORM
ARG TARGETPLATFORM
RUN echo "BUILDPLATFORM: $BUILDPLATFORM, TARGETPLATFORM: $TARGETPLATFORM"

Note: Note that ARCH should be declared before the FROM statement and can only be used within the FROM statement.

Issues

CentOS7 image does not support linux/arm/v7 and will result in an error.

ARG ARCH
FROM ${ARCH}centos:7

RUN yum install -y curl

ENTRYPOINT [ "curl" ]

Execute the command:

docker buildx build --platform linux/arm/v7 .

An error occurred and it has been stuck indefinitely:

[+] Building 29.0s (5/6) 
 => [2/2] RUN yum install -y curl                                                                                        25.7s
 => => # qemu: uncaught target signal 11 (Segmentation fault) - core dumped 

Note: Even if you switch to CentOS8, it does not support armv7.

Switching to Ubuntu20 will not be a problem.

ARG ARCH
# http://releases.ubuntu.com/focal/
FROM ${ARCH}ubuntu:focal

ENV DEBIAN_FRONTEND noninteractive
RUN apt-get update && apt-get install -y curl

ENTRYPOINT [ "curl" ]

It can be compiled on all three platforms.

docker buildx build --platform linux/arm/v7,linux/arm64/v8,linux/amd64 .

So SRS is ready to switch to the Ubuntu20 base development image.

Debug Building SRT

To compile SRT for a specific platform, such as linux/arm/v7, first package the code.

cd ~/git/srs
tar cf srs.tar trunk

Then modify trunk/Dockerfile and compile SRT directly.

ARG ARCH
FROM ${ARCH}ossrs/srs:ubuntu20 AS build

ARG BUILDPLATFORM
ARG TARGETPLATFORM
RUN echo "BUILDPLATFORM: $BUILDPLATFORM, TARGETPLATFORM: $TARGETPLATFORM"

# https://serverfault.com/questions/949991/how-to-install-tzdata-on-a-ubuntu-docker-image
ENV DEBIAN_FRONTEND noninteractive

# Install depends tools.
RUN apt-get update && apt-get install -y gcc make g++ patch unzip perl git

ARG SRS_AUTO_PACKAGER

############ TEST
ADD srs.tar /srs
WORKDIR /srs/trunk/3rdparty/srt-1-fit
RUN apt-get install -y libssl-dev
RUN ./configure --disable-app  --enable-static --enable-c++11=0 --enable-shared=0
RUN echo "CMakeOutput.log" && cat /srs/trunk/3rdparty/srt-1-fit/CMakeFiles/CMakeOutput.log
RUN echo "CMakeError.log" && cat /srs/trunk/3rdparty/srt-1-fit/CMakeFiles/CMakeError.log
RUN exit 1

Execute the command:

docker buildx create --name mybuilder --driver docker-container
docker buildx use mybuilder
cd ~/git/srs && docker buildx build --platform linux/arm/v7 -f trunk/Dockerfile --progress=plain .

This is equivalent to directly compiling SRT, with a short debugging cycle.

TRANS_BY_GPT3

@winlinvip winlinvip self-assigned this Jun 2, 2022
@winlinvip winlinvip added good first issue Easy to fix issues, good for newcomers help wanted Extra attention is needed labels Jun 2, 2022
@winlinvip winlinvip added this to the 5.0 milestone Jun 2, 2022
@finaldzn
Copy link

finaldzn commented Jun 9, 2022

I can confirm tht arm/v7 doesn't work

docker build trunk --platform=linux/arm/v7

Sending build context to Docker daemon  78.51MB

Step 1/13 : FROM ossrs/srs:dev AS build

 ---> cfe21cb0078f

Step 2/13 : RUN yum install -y gcc make gcc-c++ patch unzip perl git

 ---> [Warning] The requested image's platform (linux/amd64) does not match the detected host platform (linux/arm/v7) and no specific platform was requested

 ---> Running in d21d2c0eefb9

exec /bin/sh: exec format error
The command '/bin/sh -c yum install -y gcc make gcc-c++ patch unzip perl git' returned a non-zero code: 1


@winlinvip winlinvip changed the title Docker: Support armv7 and aarch64 docker image Docker: Support x86_64, armv7 and aarch64 docker image Jun 10, 2022
@chundonglinlin
Copy link
Member

chundonglinlin commented Jun 10, 2022

Compilation reference: v5_CN_SrsLinuxArm

TRANS_BY_GPT3

@winlinvip
Copy link
Member Author

Fixed

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
good first issue Easy to fix issues, good for newcomers help wanted Extra attention is needed TransByAI Translated by AI/GPT.
Projects
None yet
Development

No branches or pull requests

3 participants