From 691f170612b7de2993ae4c49c1aacf39624f02fe Mon Sep 17 00:00:00 2001 From: Christian Geller <88664444+cgeller@users.noreply.github.com> Date: Wed, 31 Jan 2024 16:11:01 +0100 Subject: [PATCH] Initial Release - Created GitHub workflow and Dockerfile to automatically build Docker images - Update to Ubuntu 22.04 and Python 3.10 for prerequisites image - Update to Ubuntu 22.04 and Python 3.10 for release image - Created vulkan-base Dockerfile to replace discontinued nvidia/vulkan images used for the release image - Added health check to release image - Added `ping.py` script to PythonAPI to enable health checks - Fix [aria2](https://aria2.github.io/) related issue - Fix fbx sdk download by using `curl` instead of `wget` --- .github/workflows/docker.yml | 165 ++++++++++++++++++++++ CARLOS_CHANGELOG.md | 17 +++ PythonAPI/util/ping.py | 70 +++++++++ README.md | 28 +++- Update.sh | 14 +- Util/BuildTools/BuildUtilsDocker.sh | 2 +- Util/Docker/Carla.Dockerfile | 20 ++- Util/Docker/Prerequisites.Dockerfile | 51 +++++-- Util/Docker/Release.Dockerfile | 16 ++- Util/Docker/vulkan-base/Vulkan.Dockerfile | 56 ++++++++ 10 files changed, 405 insertions(+), 34 deletions(-) create mode 100644 .github/workflows/docker.yml create mode 100644 CARLOS_CHANGELOG.md create mode 100755 PythonAPI/util/ping.py create mode 100644 Util/Docker/vulkan-base/Vulkan.Dockerfile diff --git a/.github/workflows/docker.yml b/.github/workflows/docker.yml new file mode 100644 index 00000000000..48d85da91cc --- /dev/null +++ b/.github/workflows/docker.yml @@ -0,0 +1,165 @@ +name: Docker + +on: [push, pull_request] + +jobs: + + # set up + clean-up: + name: Clean up + runs-on: self-hosted + steps: + + - name: Clean up + run: rm -rf * + + # create carla-prerequisites image + create-carla-prerequisites-image: + name: Create carla-prerequisites image + runs-on: self-hosted + needs: clean-up + steps: + + - uses: docker/build-push-action@v5 + name: Build image + with: + file: Util/Docker/Prerequisites.Dockerfile + tags: carla-prerequisites + no-cache: true + build-args: | + EPIC_USER=${{ secrets.EPIC_USER }} + EPIC_PASS=${{ secrets.EPIC_PASS }} + + # create and push carla-source image + create-carla-source-image: + name: Create carla-source image + runs-on: self-hosted + needs: create-carla-prerequisites-image + env: + IMAGE_TAG_SUFFIX: "" + + steps: + + - name: Set image tag + run: | + echo "IMAGE_TAG_SUFFIX=_$(echo '${{ github.ref_name }}' | tr / -)_ci" >> $GITHUB_ENV + if: github.ref.name != github.event.repository.default_branch + + - uses: actions/checkout@v3 + name: Checkout repository + with: + submodules: true + + - uses: docker/login-action@v3 + name: Login to Docker Hub + with: + username: ${{ secrets.DOCKER_USERNAME }} + password: ${{ secrets.DOCKER_PASSWORD }} + + - uses: docker/build-push-action@v5 + name: Build and push image + with: + file: Util/Docker/Carla.Dockerfile + tags: rwthika/carla-simulator:source${{env.IMAGE_TAG_SUFFIX}} + no-cache: true + push: false + context: . + + # provide artifacts and releases + provide-artifacts: + name: Provide carla artifacts + runs-on: self-hosted + needs: create-carla-source-image + env: + IMAGE_TAG_SUFFIX: "" + + steps: + + - name: Set image tag + run: | + echo "IMAGE_TAG_SUFFIX=_$(echo '${{ github.ref_name }}' | tr / -)_ci" >> $GITHUB_ENV + if: github.ref.name != github.event.repository.default_branch + + # provide carla-package + - uses: shrink/actions-docker-extract@v3 + name: Extract carla-package + with: + image: rwthika/carla-simulator:source${{env.IMAGE_TAG_SUFFIX}} + path: home/carla/carla/Dist + destination: artifacts/ + + # provide carla-python-api + - uses: shrink/actions-docker-extract@v3 + name: Extract carla-python-api + id: extract_python_api + with: + image: rwthika/carla-simulator:source${{env.IMAGE_TAG_SUFFIX}} + path: home/carla/carla/PythonAPI + destination: artifacts/ + + # create archive for release + - name: Create archive + if: startsWith(github.ref, 'refs/tags') + run: tar -czvf artifacts/PythonAPI.tar.gz artifacts/PythonAPI + + # provide release + - uses: ncipollo/release-action@v1 + name: Create Release + if: startsWith(github.ref, 'refs/tags') + with: + allowUpdates: true + tag: ${{ github.ref_name }} + commit: ${{ github.sha }} + artifacts: artifacts/PythonAPI.tar.gz + token: ${{ secrets.PAT }} + + # create vulkan-base for carla release + create-vulkan-base-image: + name: Create vulkan-base image + runs-on: self-hosted + needs: provide-artifacts + steps: + + - uses: docker/build-push-action@v5 + name: Build image + with: + file: Util/Docker/vulkan-base/Vulkan.Dockerfile + tags: vulkan-base + no-cache: true + build-args: | + BASE_DIST=ubuntu22.04 + CUDA_VERSION=12.2.0 + context: Util/Docker/vulkan-base + + # create and push carla image + create-carla-image: + name: Create carla image + runs-on: self-hosted + needs: create-vulkan-base-image + env: + IMAGE_TAG_SUFFIX: "" + + steps: + + - name: Set image tag + run: | + echo "IMAGE_TAG_SUFFIX=_$(echo '${{ github.ref_name }}' | tr / -)_ci" >> $GITHUB_ENV + if: github.ref.name != github.event.repository.default_branch + + - uses: docker/login-action@v3 + name: Login to Docker Hub + with: + username: ${{ secrets.DOCKER_USERNAME }} + password: ${{ secrets.DOCKER_PASSWORD }} + + - name: Extract artifact + run: mkdir -p build && tar -xvzf artifacts/Dist/*.tar.gz -C build + + - uses: docker/build-push-action@v5 + name: Build and push + with: + file: build/Dockerfile + tags: rwthika/carla-simulator:latest${{env.IMAGE_TAG_SUFFIX}} + no-cache: true + context: build + push: true diff --git a/CARLOS_CHANGELOG.md b/CARLOS_CHANGELOG.md new file mode 100644 index 00000000000..8bd7c3b2dbe --- /dev/null +++ b/CARLOS_CHANGELOG.md @@ -0,0 +1,17 @@ +## Latest : 1.0.0 + +## 1.0.0 - Initial Release + +### Major changes + +* Created GitHub workflow and Dockerfile to automatically build Docker images +* Update to Ubuntu 22.04 and Python 3.10 for prerequisites image +* Update to Ubuntu 22.04 and Python 3.10 for release image +* Created `vulkan-base` Dockerfile to replace discontinued `nvidia/vulkan` images used for the release image +* Added health check to release image + +### Minor changes + +* Added `ping.py` script to PythonAPI to enable health checks +* Fix [aria2](https://aria2.github.io/) related issue +* Fix fbx sdk download by using `curl` instead of `wget` diff --git a/PythonAPI/util/ping.py b/PythonAPI/util/ping.py new file mode 100755 index 00000000000..dac97d682ad --- /dev/null +++ b/PythonAPI/util/ping.py @@ -0,0 +1,70 @@ +#!/usr/bin/env python + +# Copyright (c) 2019 Computer Vision Center (CVC) at the Universitat Autonoma de +# Barcelona (UAB). +# +# This work is licensed under the terms of the MIT license. +# For a copy, see . + +"""Performs a single connection check to the simulator.""" + +import glob +import os +import sys + +try: + os.chdir(os.path.dirname(__file__)) + sys.path.append(glob.glob('../carla/dist/carla-*%d.%d-%s.egg' % ( + sys.version_info.major, + sys.version_info.minor, + 'win-amd64' if os.name == 'nt' else 'linux-x86_64'))[0]) +except IndexError: + pass + + +import carla + +import argparse + + +def main(): + argparser = argparse.ArgumentParser( + description=__doc__) + argparser.add_argument( + '--host', + metavar='H', + default='127.0.0.1', + help='IP of the host server (default: 127.0.0.1)') + argparser.add_argument( + '-p', '--port', + metavar='P', + default=2000, + type=int, + help='TCP port to listen to (default: 2000)') + argparser.add_argument( + '--timeout', + metavar='T', + default=1.0, + type=float, + help='time-out in seconds (default: 1)') + args = argparser.parse_args() + + try: + client = carla.Client(args.host, args.port) + except RuntimeError: + print('IP/Hostname %s could not be resolved' % (args.host)) + return 1 + + client.set_timeout(args.timeout) + + try: + print('CARLA %s connected at %s:%d.' % (client.get_server_version(), args.host, args.port)) + return 0 + except RuntimeError: + print('Failed to connect to %s:%d before time-out of %d second(s).' % (args.host, args.port, args.timeout)) + return 1 + + +if __name__ == '__main__': + + sys.exit(main()) diff --git a/README.md b/README.md index 98086e0c0c3..b9725852b04 100644 --- a/README.md +++ b/README.md @@ -1,5 +1,29 @@ -CARLA Simulator -=============== +# Simulation Core: *carla-simulator* + +

+ + + + + + + +

+ +> [!IMPORTANT] +> This repository is a minimal fork of the official [carla-simulator](https://github.com/carla-simulator/carla)! All modifications to the original repository are documented in [CARLOS_CHANGELOG.md](./CARLOS_CHANGELOG.md). + +> [!TIP] +> We recommend to use the *carla-simulator* as **simulation core** in our open, modular and scalable simulation framework **CARLOS**. +> +> Here, it constitutes the central element of a simulation and handles all graphical and dynamic calculations in the individual simulation time steps. + +> [!NOTE] +> We set up a Continous Integration (CI) pipeline as [GitHub workflow](./github/workflows/docker.yml) to continously build Docker images for the `carla-simulator`, publicly available on [Docker Hub](https://hub.docker.com/r/rwthika/carla-simulator). + +--- +--- +## Original README [![Build Status](https://travis-ci.org/carla-simulator/carla.svg?branch=master)](https://travis-ci.org/carla-simulator/carla) [![Documentation](https://readthedocs.org/projects/carla/badge/?version=latest)](http://carla.readthedocs.io) diff --git a/Update.sh b/Update.sh index 72ed6390727..cbd579f1fcd 100755 --- a/Update.sh +++ b/Update.sh @@ -58,13 +58,15 @@ function download_content { fi mkdir -p "$CONTENT_FOLDER" mkdir -p Content - if hash aria2c 2>/dev/null; then - echo -e "${CONTENT_LINK}\n\tout=Content.tar.gz" > .aria2c.input - aria2c -j16 -x16 --input-file=.aria2c.input - rm -f .aria2c.input - else + + #if hash aria2c 2>/dev/null; then + # echo -e "${CONTENT_LINK}\n\tout=Content.tar.gz" > .aria2c.input + # aria2c -j16 -x16 --input-file=.aria2c.input + # rm -f .aria2c.input + #else wget -c ${CONTENT_LINK} -O Content.tar.gz - fi + #fi + tar -xvzf Content.tar.gz -C Content rm Content.tar.gz mv Content/* "$CONTENT_FOLDER" diff --git a/Util/BuildTools/BuildUtilsDocker.sh b/Util/BuildTools/BuildUtilsDocker.sh index 2c85a7b053c..6689d0bfb77 100755 --- a/Util/BuildTools/BuildUtilsDocker.sh +++ b/Util/BuildTools/BuildUtilsDocker.sh @@ -17,7 +17,7 @@ FBXSDK_URL=https://www.autodesk.com/content/dam/autodesk/www/adn/fbx/2020-0-1/${ if [ ! -d "${FBX2OBJ_DEP_FOLDER}" ]; then log "Downloading FBX SDK..." - wget -c "${FBXSDK_URL}" -P "${CARLA_DOCKER_UTILS_FOLDER}" --user-agent="Mozilla" + curl -L "${FBXSDK_URL}" -o "${CARLA_DOCKER_UTILS_FOLDER}/${LIB_NAME}.tar.gz" --user-agent "Mozilla" echo "Unpacking..." mkdir -p "${FBX2OBJ_DEP_FOLDER}" diff --git a/Util/Docker/Carla.Dockerfile b/Util/Docker/Carla.Dockerfile index 65f5d67dd5d..a9343bed201 100644 --- a/Util/Docker/Carla.Dockerfile +++ b/Util/Docker/Carla.Dockerfile @@ -3,17 +3,15 @@ FROM carla-prerequisites:latest ARG GIT_BRANCH USER carla -WORKDIR /home/carla -RUN cd /home/carla/ && \ - if [ -z ${GIT_BRANCH+x} ]; then git clone --depth 1 https://github.com/carla-simulator/carla.git; \ - else git clone --depth 1 --branch $GIT_BRANCH https://github.com/carla-simulator/carla.git; fi && \ - cd /home/carla/carla && \ - ./Update.sh && \ - make CarlaUE4Editor && \ - make PythonAPI && \ - make build.utils && \ - make package && \ - rm -r /home/carla/carla/Dist +COPY --chown=carla . /home/carla/carla WORKDIR /home/carla/carla + +RUN pip3 install -Iv setuptools==47.3.1 + +RUN ./Update.sh +RUN make CarlaUE4Editor +RUN make PythonAPI ARGS="--python-version='3.10'" +RUN make build.utils +RUN make package ARGS="--clean-intermediate" diff --git a/Util/Docker/Prerequisites.Dockerfile b/Util/Docker/Prerequisites.Dockerfile index 7cd78116707..0c11b6b05a1 100644 --- a/Util/Docker/Prerequisites.Dockerfile +++ b/Util/Docker/Prerequisites.Dockerfile @@ -1,4 +1,4 @@ -FROM ubuntu:18.04 +FROM nvidia/cuda:11.3.1-runtime-ubuntu20.04 USER root @@ -8,8 +8,7 @@ ENV DEBIAN_FRONTEND=noninteractive RUN apt-get update ; \ apt-get install -y wget software-properties-common && \ add-apt-repository ppa:ubuntu-toolchain-r/test && \ - wget -O - https://apt.llvm.org/llvm-snapshot.gpg.key|apt-key add - && \ - apt-add-repository "deb http://apt.llvm.org/xenial/ llvm-toolchain-xenial-8 main" && \ + add-apt-repository ppa:deadsnakes/ppa && \ apt-get update ; \ apt-get install -y build-essential \ clang-8 \ @@ -18,11 +17,13 @@ RUN apt-get update ; \ cmake \ ninja-build \ libvulkan1 \ + libvulkan-dev \ + vulkan-tools \ + libglvnd-dev \ python \ - python-pip \ - python-dev \ - python3-dev \ - python3-pip \ + python3.10 \ + python3.10-dev \ + python3.10-distutils \ libpng-dev \ libtiff5-dev \ libjpeg-dev \ @@ -35,13 +36,41 @@ RUN apt-get update ; \ rsync \ libxml2-dev \ git \ - aria2 && \ - pip3 install -Iv setuptools==47.3.1 && \ - pip3 install distro && \ + aria2 + +# Install pip for python 3.10 +RUN curl https://bootstrap.pypa.io/get-pip.py -o get-pip.py && \ + python3.10 get-pip.py && \ + rm get-pip.py + +# Install Python Packages +RUN pip3.10 install -Iv setuptools==47.3.1 && \ + pip3.10 install distro && \ + pip3.10 install pygame && \ + pip3.10 install numpy + +# Set Alternatives and Defaults +RUN update-alternatives --install /usr/bin/python3 python3 /usr/bin/python3.10 1 && \ + update-alternatives --set python3 /usr/bin/python3.10 && \ update-alternatives --install /usr/bin/clang++ clang++ /usr/lib/llvm-8/bin/clang++ 180 && \ update-alternatives --install /usr/bin/clang clang /usr/lib/llvm-8/bin/clang 180 -RUN useradd -m carla +# Enable Vulkan support for NVIDIA GPUs +RUN apt-get update && apt-get install -y --no-install-recommends libvulkan1 && \ + rm -rf /var/lib/apt/lists/* && \ + VULKAN_API_VERSION=`dpkg -s libvulkan1 | grep -oP 'Version: [0-9|\.]+' | grep -oP '[0-9|\.]+'` && \ + mkdir -p /etc/vulkan/icd.d/ && \ + echo \ + "{\ + \"file_format_version\" : \"1.0.0\",\ + \"ICD\": {\ + \"library_path\": \"libGLX_nvidia.so.0\",\ + \"api_version\" : \"${VULKAN_API_VERSION}\"\ + }\ + }" > /etc/vulkan/icd.d/nvidia_icd.json + +# Setup carla and UnrealEngine +RUN useradd -m carla && echo "carla:carla" | chpasswd && adduser carla sudo COPY --chown=carla:carla . /home/carla USER carla WORKDIR /home/carla diff --git a/Util/Docker/Release.Dockerfile b/Util/Docker/Release.Dockerfile index 39d4b6d47a9..590ca15f165 100644 --- a/Util/Docker/Release.Dockerfile +++ b/Util/Docker/Release.Dockerfile @@ -3,9 +3,7 @@ # # sudo -E docker run --rm --gpus all -it --net=host carla:latest /bin/bash -FROM nvidia/vulkan:1.1.121-cuda-10.1--ubuntu18.04 - -RUN apt-key adv --fetch-keys "https://developer.download.nvidia.com/compute/cuda/repos/ubuntu1804/x86_64/3bf863cc.pub" +FROM vulkan-base:latest RUN packages='libsdl2-2.0 xserver-xorg libvulkan1 libomp5' && apt-get update && DEBIAN_FRONTEND=noninteractive apt-get install -y $packages --no-install-recommends @@ -13,9 +11,21 @@ RUN useradd -m carla COPY --chown=carla:carla . /home/carla +# Create env setup script to make CARLA PythonAPI easily accessible (needs interactive shell!) +ARG CARLA_PYAPI_PATH=/home/carla/PythonAPI +ENV CARLA_PYAPI_PATH=${CARLA_PYAPI_PATH} + +RUN echo "export PYTHONPATH=\$PYTHONPATH:$CARLA_PYAPI_PATH/carla/dist/$(ls $CARLA_PYAPI_PATH/carla/dist | grep .egg)" >> $CARLA_PYAPI_PATH/setup_env.sh; \ + echo "export PYTHONPATH=\$PYTHONPATH:$CARLA_PYAPI_PATH/carla/agents" >> $CARLA_PYAPI_PATH/setup_env.sh; \ + echo "export PYTHONPATH=\$PYTHONPATH:$CARLA_PYAPI_PATH/carla" >> $CARLA_PYAPI_PATH/setup_env.sh; \ + echo "source $CARLA_PYAPI_PATH/setup_env.sh" >> /etc/bash.bashrc + USER carla WORKDIR /home/carla +HEALTHCHECK --interval=1s --timeout=5s --start-period=10s --retries=3 \ + CMD python3 ./PythonAPI/util/ping.py + # you can also run CARLA in offscreen mode with -RenderOffScreen # CMD /bin/bash CarlaUE4.sh -RenderOffScreen CMD /bin/bash CarlaUE4.sh diff --git a/Util/Docker/vulkan-base/Vulkan.Dockerfile b/Util/Docker/vulkan-base/Vulkan.Dockerfile new file mode 100644 index 00000000000..6f1462d446d --- /dev/null +++ b/Util/Docker/vulkan-base/Vulkan.Dockerfile @@ -0,0 +1,56 @@ +# Custom Dockerfile for the release base image (based off of discontinued https://gitlab.com/nvidia/container-images/vulkan ) + +ARG DEBIAN_FRONTEND=noninteractive +ARG BASE_DIST=ubuntu22.04 +ARG CUDA_VERSION=12.2.0 + +FROM nvidia/cuda:${CUDA_VERSION}-base-${BASE_DIST} + +RUN apt-get update && apt-get install -y --no-install-recommends \ + libglvnd0 \ + libgl1 \ + libglx0 \ + libegl1 \ + libgles2 \ + libxcb1-dev \ + libjpeg8 \ + libtiff5 \ + wget \ + xz-utils \ + && rm -rf /var/lib/apt/lists/* + +# Install Vulkan SDK +# You can set VULKAN_SDK_VERSION as latest via build-arg=`curl https://vulkan.lunarg.com/sdk/latest/linux.txt` +ARG VULKAN_SDK_VERSION=1.3.268.0 +ARG VULKAN_API_VERSION=1.3.268 +# Download the Vulkan SDK and extract the headers, loaders, layers and binary utilities +RUN wget -q --show-progress \ + --progress=bar:force:noscroll \ + https://sdk.lunarg.com/sdk/download/${VULKAN_SDK_VERSION}/linux/vulkansdk-linux-x86_64-${VULKAN_SDK_VERSION}.tar.xz \ + -O /tmp/vulkansdk-linux-x86_64-${VULKAN_SDK_VERSION}.tar.gz \ + && echo "Installing Vulkan SDK ${VULKAN_SDK_VERSION}" \ + && mkdir -p /opt/vulkan \ + && tar -xf /tmp/vulkansdk-linux-x86_64-${VULKAN_SDK_VERSION}.tar.gz -C /opt/vulkan \ + && mkdir -p /usr/local/include/ && cp -ra /opt/vulkan/${VULKAN_SDK_VERSION}/x86_64/include/* /usr/local/include/ \ + && mkdir -p /usr/local/lib && cp -ra /opt/vulkan/${VULKAN_SDK_VERSION}/x86_64/lib/* /usr/local/lib/ \ + && cp -a /opt/vulkan/${VULKAN_SDK_VERSION}/x86_64/lib/libVkLayer_*.so /usr/local/lib \ + && mkdir -p /usr/local/share/vulkan/explicit_layer.d \ + && cp /opt/vulkan/${VULKAN_SDK_VERSION}/x86_64/etc/vulkan/explicit_layer.d/VkLayer_*.json /usr/local/share/vulkan/explicit_layer.d \ + && mkdir -p /usr/local/share/vulkan/registry \ + && cp -a /opt/vulkan/${VULKAN_SDK_VERSION}/x86_64/share/vulkan/registry/* /usr/local/share/vulkan/registry \ + && cp -a /opt/vulkan/${VULKAN_SDK_VERSION}/x86_64/bin/* /usr/local/bin \ + && ldconfig \ + && rm /tmp/vulkansdk-linux-x86_64-${VULKAN_SDK_VERSION}.tar.gz && rm -rf /opt/vulkan + +# Generate Nvidia driver config +RUN mkdir -p /etc/vulkan/icd.d && \ + echo "{" > /etc/vulkan/icd.d/nvidia_icd.json; \ + echo " \"file_format_version\" : \"1.0.0\"," >> /etc/vulkan/icd.d/nvidia_icd.json; \ + echo " \"ICD\": {" >> /etc/vulkan/icd.d/nvidia_icd.json; \ + echo " \"library_path\": \"libGLX_nvidia.so.0\"," >> /etc/vulkan/icd.d/nvidia_icd.json; \ + echo " \"api_version\" : \"${VULKAN_API_VERSION}\"" >> /etc/vulkan/icd.d/nvidia_icd.json; \ + echo " }" >> /etc/vulkan/icd.d/nvidia_icd.json; \ + echo "}" >> /etc/vulkan/icd.d/nvidia_icd.json + +# Setup the required capabilities for the container runtime +ENV NVIDIA_DRIVER_CAPABILITIES compute,graphics,utility