-
-
Save shmerl/f4e5f76871239158cf083e37c5da56f4 to your computer and use it in GitHub Desktop.
#!/bin/bash | |
# Notes: | |
# | |
# 1. Works for tags and specific hash commits too (override mesa_branch variable with needed value). | |
# | |
# 2. By default builds for /opt/mesa-<branch> and places the result in ${HOME}/mnt/vmshare/mesa-<branch> | |
# You can override the build deployment location by setting dest_dir. For example this should put it right away | |
# in /opt/mesa-<branch> | |
# | |
# dest_dir=/ mesa_debian_build.sh | |
# | |
# 3. You can override the Mesa repo and resulting Mesa directory name. For instance, to build Mesa with ray tracing fixes | |
# (that development repo is picked just as an example): | |
# | |
# mesa_repo='https://gitlab.freedesktop.org/bnieuwenhuizen/mesa.git' mesa_branch='stable-rt-handles' mesa_dir='/opt/mesa-rt' mesa_debian_build.sh | |
# | |
# 4. To use latest llvm snapshot, make sure to configure llvm respository for Debian. | |
# For example, create the following apt list: /etc/apt/sources.list.d/llvm.list | |
# | |
# deb http://apt.llvm.org/unstable/ llvm-toolchain main | |
# deb-src http://apt.llvm.org/unstable/ llvm-toolchain main | |
# | |
# Sometimes you might want to enable Debian experimental repo for specific version of llvm that's older than latest snapshot, but newer | |
# than ones in other Debian repos. | |
# | |
# 5. Make sure deb-src section is configured for your Debian distro in your apt sources. That's needed to install build development packages. | |
# | |
mesa_branch=${mesa_branch:-"main"} | |
mesa_repo=${mesa_repo:-"https://gitlab.freedesktop.org/mesa/mesa.git"} | |
base_dir=${base_dir:-"${HOME}/build/mesa"} | |
src_dir=${src_dir:-"${base_dir}/source"} | |
build_dir=${build_dir:-"${base_dir}/build"} | |
patches_dir=${patches_dir:-"${base_dir}/patches"} | |
use_llvm=${use_llvm:-true} | |
llvm_ver=${llvm_ver:-"20"} | |
cpuarch=${cpuarch:-"znver4"} # Zen 4 by default. Change to your arch or "native" accordingly. | |
build_32=${build_32:-false} # Don't build 32-bit by default - needs fixing to work | |
build_debug=${build_debug:-false} | |
verbose=${verbose:-false} | |
update_sources=${update_sources:-true} | |
reset_sources=${reset_sources:-true} | |
apply_patches=${apply_patches:-true} | |
if [[ "$mesa_branch" != "mesa"* ]]; then | |
mesa_dir=${mesa_dir:-"/opt/mesa-${mesa_branch}"} | |
else | |
mesa_dir=${mesa_dir:-"/opt/${mesa_branch}"} | |
fi | |
dest_dir=${dest_dir:-"${HOME}/mnt/vmshare/$(basename ${mesa_dir})"} | |
arch_dir["32"]="x86" | |
arch_dir["64"]="x86_64" | |
function assert() { | |
rc=$1 | |
message="$2" | |
if ((rc != 0)); then | |
echo $message | |
exit $rc | |
fi | |
} | |
function ensure() { | |
local rc=1 | |
while (($rc != 0)); do | |
$@ | |
rc=$? | |
if (($rc != 0)); then | |
sleep 1 | |
fi | |
done | |
} | |
function common_prepare() { | |
echo "=== Common setup ====" | |
mkdir -p ${dest_dir} | |
rm -rfv ${dest_dir}/${mesa_dir}/* | |
ensure sudo apt-get install build-essential git | |
# Potential clean up of previously created repo directory due to repo URL mismatch. | |
if [[ -e "$src_dir" ]]; then | |
cd "$src_dir" | |
local prev_mesa_repo=$(git config --get remote.origin.url) | |
if [[ "$prev_mesa_repo" != "$mesa_repo" ]]; then | |
cd $(dirname "$src_dir") | |
rm -rfv $(basename "$src_dir") | |
fi | |
fi | |
cd $(dirname "$src_dir") | |
if ! [[ -e "$src_dir" ]]; then | |
git clone "$mesa_repo" $(basename "$src_dir") | |
fi | |
cd "$src_dir" | |
# If updating, reset is enforced regardless of the $reset_sources, to avoid possible merging confusion. | |
if $reset_sources || $update_sources; then | |
git reset --hard HEAD | |
git clean -df | |
fi | |
if $update_sources; then | |
git checkout main | |
git pull --rebase --prune | |
git checkout $mesa_branch | |
if (($? != 0)); then | |
echo "Invalid branch or tag ${mesa_branch}! Aborting" | |
exit 2 | |
fi | |
fi | |
if $apply_patches; then | |
mkdir -p "$patches_dir" | |
for patch in ${patches_dir}/*; do | |
patch -p 1 < ${patch} | |
assert $? "Failed to apply patch ${patch}" | |
done | |
fi | |
mkdir -p "$build_dir" | |
rm -rfv ${build_dir}/* | |
} | |
function prepare_64() { | |
echo "=== Preparing 64-bit build ====" | |
ensure sudo apt-get build-dep mesa | |
if $use_llvm; then | |
ensure sudo apt-get install llvm-${llvm_ver}-dev libclang-${llvm_ver}-dev libpolly-${llvm_ver}-dev | |
fi | |
} | |
function prepare_32() { | |
echo "==== Preparing 32-bit build ====" | |
# TODO: all this needs a working method in Debian | |
echo "Not supported now" | |
return | |
ensure sudo apt-get install llvm-${llvm_ver}-dev:i386 libclang-${llvm_ver}-dev:i386 gcc-multilib g++-multilib libdrm-dev:i386 libexpat1-dev:i386 libxcb-dri3-dev:i386 libxcb-present-dev:i386 libxshmfence-dev:i386 libxext-dev:i386 libxdamage-dev:i386 libx11-xcb-dev:i386 libxcb-glx0-dev:i386 libxcb-dri2-0-dev:i386 libxxf86vm-dev:i386 libwayland-dev:i386 libsensors4-dev:i386 libelf-dev:i386 zlib1g-dev:i386 libglvnd-core-dev:i386 | |
} | |
configure_64() { | |
echo "==== Configuring 64-bit build ====" | |
cd "$build_dir" | |
local build_type='plain' | |
local debug_flags='' | |
local ndebug=true | |
local strip_option='--strip' | |
if $build_debug; then | |
build_type='debug' | |
debug_flags='-g' | |
ndebug=false | |
strip_option='' | |
fi | |
local llvm_val='disabled' | |
if $use_llvm; then | |
llvm_val='enabled' | |
fi | |
local native_config | |
read -r -d '' native_config <<EOF | |
[binaries] | |
llvm-config = '/usr/bin/llvm-config-${llvm_ver}' | |
cmake = '/usr/bin/false' | |
EOF | |
export CFLAGS="-march=${cpuarch} ${debug_flags} -O2 -ffile-prefix-map=${HOME}/build=. -fstack-protector-strong -Wformat -Werror=format-security -Wall" | |
export CPPFLAGS="-Wdate-time -D_FORTIFY_SOURCE=2" | |
export CXXFLAGS="-march=${cpuarch} ${debug_flags} -O2 -ffile-prefix-map=${HOME}/build=. -fstack-protector-strong -Wformat -Werror=format-security -Wall" | |
export LDFLAGS="-Wl,-z,relro" | |
LC_ALL=C.UTF-8 meson setup "$src_dir" \ | |
--wrap-mode=nodownload \ | |
--buildtype=$build_type \ | |
$strip_option \ | |
--native-file=<(echo "$native_config") \ | |
--prefix="$mesa_dir" \ | |
--sysconfdir=/etc \ | |
--localstatedir=/var \ | |
--libdir="${arch_dir["64"]}" \ | |
-D dri-drivers-path="${arch_dir["64"]}" \ | |
-D platforms="['x11','wayland']" \ | |
-D vulkan-drivers="['amd']" \ | |
-D vulkan-layers="['device-select','overlay']" \ | |
-D glvnd=enabled \ | |
-D shared-glapi=enabled \ | |
-D b_ndebug=$ndebug \ | |
-D glx-direct=true \ | |
-D gbm=enabled \ | |
-D gallium-extra-hud=true \ | |
-D gallium-vdpau=disabled \ | |
-D lmsensors=enabled \ | |
-D llvm=$llvm_val \ | |
-D shared-llvm=disabled \ | |
-D gallium-va=enabled \ | |
-D va-libs-path="${arch_dir["64"]}" \ | |
-D video-codecs=all \ | |
-D gallium-drivers="['radeonsi','zink']" \ | |
-D gles1=disabled \ | |
-D gles2=enabled \ | |
-D sse2=true \ | |
-D teflon=false | |
assert $? "Configure failed!" | |
} | |
configure_32() { | |
echo "==== Configuring 32-bit ====" | |
echo "Not supported now" | |
return | |
} | |
function build() { | |
echo "==== Building... ====" | |
cd "$build_dir" | |
if $verbose; then | |
LC_ALL=C.UTF-8 ninja -v | |
else | |
LC_ALL=C.UTF-8 ninja | |
fi | |
assert $? "build failed!" | |
} | |
function publish() { | |
cd "$build_dir" | |
DESTDIR="$dest_dir" LC_ALL=C.UTF-8 ninja install | |
} | |
function clean_64() { | |
if $use_llvm; then | |
ensure sudo apt-get purge llvm-${llvm_ver}-dev libclang-${llvm_ver}-dev libpolly-${llvm_ver}-dev | |
fi | |
ensure sudo apt-get autoremove --purge | |
} | |
function clean_32() { | |
ensure sudo apt-get purge llvm-${llvm_ver}-dev:i386 libclang-${llvm_ver}-dev:i386 libsensors4-dev:i386 | |
ensure sudo apt-get autoremove --purge | |
} | |
################################################ | |
shopt -s nullglob | |
common_prepare | |
prepare_64 | |
configure_64 | |
build | |
publish | |
clean_64 | |
if ! $build_32; then | |
exit | |
fi | |
prepare_32 | |
configure_32 | |
build | |
publish | |
clean_32 |
I didn't try using it with stable (running it on testing usually). In order to use llvm 11, you might need the llvm repo, see note #4:
# 4. To use latest llvm snapshot, make sure to configure llvm respository for Debian.
# For example, create the following apt list: /etc/apt/sources.list.d/llvm.list
#
# deb http://apt.llvm.org/unstable/ llvm-toolchain main
# deb-src http://apt.llvm.org/unstable/ llvm-toolchain main
Also, see this bug: https://gitlab.freedesktop.org/mesa/mesa/-/issues/2843
Mesa developers still didn't fix it.
Fixed the empty directory issue, please test.
Fixed the empty directory issue, please test.
where is the fixed code? In another gist? I would like to test, if the problem is solved.
I'm now on Debian bullseye and I can compile the it.
Can you put this script under an official open source licence? I would like to contribute some improvements, for example when you don't use deb-src from bullyseye, yo get an endless loop.
Same gist.
Good point on the need to use deb-src, I have it. I'll add a comment about it to make it more obvious.
great it's working
Hello @shmerl ,
I tried today to run this script on my debian buster VM to build Mesa 20.0.7 and I have some trouble to run it, because I the script have some problems with libclang-11-dev and llvm-11-dev, I also tried version 7, which is the default version on Debian Buster
Whats the correct version or is there some other problem?
It's also not a problem to build it on sid, but I don't know, if Mesa 20.0.7 is working on Debian Buster.
The script crashed btw at this lines:
because in the patch directory was empty.