2016-10-18 01:22:46 -07:00
|
|
|
#!/usr/bin/env zsh
|
|
|
|
|
2017-03-30 19:11:05 -07:00
|
|
|
# I'll just leave this here
|
|
|
|
__setup_clang_ubuntu() {
|
|
|
|
local site="http://apt.llvm.org"
|
|
|
|
local name="$(lsb_release -c | cut -f2)"
|
2017-03-30 19:46:30 -07:00
|
|
|
local version=4.0
|
|
|
|
local priority=$(( int(version * 100 + 0.5) ))
|
2017-03-30 19:11:05 -07:00
|
|
|
# TODO: use https? this is sketchy
|
|
|
|
echo wget -O - "$site/llvm-snapshot.gpg.key" \| apt-key add -
|
|
|
|
echo echo -n \""\
|
|
|
|
deb $site/$name/ llvm-toolchain-$name main\n\
|
|
|
|
# deb-src $site/$name/ llvm-toolchain-$name main\n\
|
|
|
|
# $version\n\
|
|
|
|
deb $site/$name/ llvm-toolchain-$name-$version main\n\
|
|
|
|
# deb-src $site/$name/ llvm-toolchain-$name-$version main\n\
|
|
|
|
"\" \> "/etc/apt/sources.list.d/llvm-toolchain-$name.list"
|
|
|
|
echo apt-get update
|
|
|
|
echo apt-get install clang-$version
|
|
|
|
echo apt-get install lld-$version
|
2017-03-30 19:46:30 -07:00
|
|
|
echo update-alternatives --install /usr/bin/clang clang /usr/bin/clang-$version $priority
|
|
|
|
echo update-alternatives --install /usr/bin/clang++ clang++ /usr/bin/clang++-$version $priority
|
|
|
|
echo update-alternatives --install /usr/bin/llvm-symbolizer llvm-symbolizer /usr/bin/llvm-symbolizer-$version $priority
|
2017-03-30 19:11:05 -07:00
|
|
|
}
|
|
|
|
|
2016-10-18 01:22:46 -07:00
|
|
|
compile() {
|
|
|
|
if [ $# -lt 2 ]; then
|
|
|
|
echo "usage: compile [clang|gcc] {debug|release} [flags...] {source file}" >&2
|
|
|
|
return 1
|
|
|
|
fi
|
|
|
|
|
|
|
|
local sepples=0
|
|
|
|
local CC=gcc
|
|
|
|
local CXX=g++
|
2016-10-19 04:31:33 -07:00
|
|
|
local our_flags=(-I.)
|
|
|
|
|
|
|
|
maybe_include() {
|
|
|
|
[ -d "$1" ] && our_flags+=("-I$1")
|
|
|
|
}
|
|
|
|
maybe_include "-I$HOME/opt/local/include"
|
|
|
|
maybe_include "-I$HOME/src/ustl"
|
|
|
|
|
2017-04-01 19:17:40 -07:00
|
|
|
local debug_flags=(-O1 -g -D_DEBUG);
|
2016-10-18 01:22:46 -07:00
|
|
|
local release_flags=(-Ofast -march=native -g0 -fomit-frame-pointer -s -DNDEBUG)
|
|
|
|
local dr_flags=(-Ofast -march=native -g -fomit-frame-pointer -DNDEBUG)
|
2017-03-30 20:49:47 -07:00
|
|
|
local hardened_flags=(-O3 -march=native -g0 -s
|
|
|
|
-DNDEBUG -D_FORTIFY_SOURCE=2
|
|
|
|
-Wformat -Wformat-security -Werror=format-security)
|
|
|
|
|
2017-04-02 03:37:49 -07:00
|
|
|
if [ -z "$MSYSTEM" ]; then
|
2017-03-30 20:49:47 -07:00
|
|
|
hardened_flags+=(-fPIE -pie)
|
|
|
|
hardened_flags+=(-Wl,-O1,--sort-common,--as-needed,-z,relro,-z,now)
|
|
|
|
fi
|
2016-10-18 01:22:46 -07:00
|
|
|
|
2017-04-02 03:37:49 -07:00
|
|
|
local tcmalloc=(-ltcmalloc -fno-builtin-malloc -fno-builtin-calloc -fno-builtin-realloc -fno-builtin-free)
|
2016-10-18 01:22:46 -07:00
|
|
|
if [ -e /usr/bin/pprof ]; then
|
2017-04-02 03:37:49 -07:00
|
|
|
debug_flags+=($tcmalloc)
|
|
|
|
dr_flags+=($tcmalloc -lprofiler)
|
|
|
|
elif [ -e /usr/bin/google-pprof ]; then
|
|
|
|
debug_flags+=(-l:libtcmalloc.so.4 ${tcmalloc[2,-1]})
|
|
|
|
dr_flags+=(-l:libtcmalloc_and_profiler.so.4 ${tcmalloc[2,-1]})
|
2016-10-18 01:22:46 -07:00
|
|
|
fi
|
|
|
|
|
|
|
|
local file=${@[-1]}
|
2017-03-30 18:09:26 -07:00
|
|
|
[ "${file##*.}" = "c" ] || [ "${file##*.}" = "h" ] || sepples=1
|
2016-10-18 01:22:46 -07:00
|
|
|
|
|
|
|
{ [ $1 = clang ] && CC="clang" && CXX="clang++" && shift } || \
|
|
|
|
{ [ $1 = gcc ] && CC="gcc" && CXX="g++" && shift }
|
|
|
|
|
2017-04-01 15:27:46 -07:00
|
|
|
if [ $CC = clang ]; then
|
2017-03-30 18:09:26 -07:00
|
|
|
debug_flags+=(-ftrapv)
|
2017-04-02 03:37:49 -07:00
|
|
|
if [ -z "$MSYSTEM" ]; then # only available on linux
|
2017-03-30 18:09:26 -07:00
|
|
|
debug_flags+=(-fsanitize=undefined) # this SHOULD work with mingw,
|
|
|
|
# but it fails to link.
|
|
|
|
debug_flags+=(-fsanitize=address)
|
2017-03-30 20:49:47 -07:00
|
|
|
debug_flags+=(-fvisibility=hidden -fuse-ld=gold -flto -fsanitize=cfi)
|
|
|
|
|
|
|
|
hardened_flags+=(-fsanitize=safe-stack)
|
|
|
|
hardened_flags+=(-fstack-protector-strong)
|
|
|
|
hardened_flags+=(-fvisibility=hidden -fuse-ld=gold -flto -fsanitize=cfi)
|
2017-04-01 15:27:46 -07:00
|
|
|
else
|
|
|
|
our_flags+=(-fansi-escape-codes)
|
2017-03-30 18:09:26 -07:00
|
|
|
fi
|
|
|
|
fi
|
|
|
|
|
2016-10-18 01:22:46 -07:00
|
|
|
{ [ $1 = debug ] && our_flags+=($debug_flags) && shift } || \
|
|
|
|
{ [ $1 = release ] && our_flags+=($release_flags) && shift } || \
|
2016-10-19 04:31:33 -07:00
|
|
|
{ [ $1 = derelease ] && our_flags+=($dr_flags) && shift } || \
|
2017-03-30 20:49:47 -07:00
|
|
|
{ [ $1 = hardened ] && our_flags+=($hardened_flags) && shift } || \
|
|
|
|
{ echo "please specify either debug or (de)release or hardened" >&2; return 1 }
|
2016-10-18 01:22:46 -07:00
|
|
|
|
|
|
|
# TODO add static option
|
|
|
|
|
|
|
|
local compiler=
|
|
|
|
if [ $sepples -eq 1 ]; then
|
|
|
|
compiler=$CXX
|
|
|
|
std="-std=gnu++1z"
|
|
|
|
else
|
|
|
|
compiler=$CC
|
|
|
|
std="-std=gnu11"
|
|
|
|
fi
|
|
|
|
|
|
|
|
local flags=(${@[1,-2]})
|
|
|
|
|
|
|
|
local out=/tmp/${${file%%.*}##*/}
|
2017-04-02 03:37:49 -07:00
|
|
|
if [ -n "$MSYSTEM" ]; then
|
2017-04-01 19:17:40 -07:00
|
|
|
# explicitly output to .exe to avoid weirdness
|
|
|
|
out="$out.exe"
|
|
|
|
fi
|
2016-10-18 01:22:46 -07:00
|
|
|
|
2017-03-30 19:11:05 -07:00
|
|
|
# TODO: naive idea:
|
|
|
|
# allow multiple source files (using the firstmost to determine the program name)
|
|
|
|
# by generating a file that #includes each given file.
|
|
|
|
|
2017-04-02 03:37:49 -07:00
|
|
|
# move -l flags to the end because gcc won't respect them otherwise
|
|
|
|
local final_flags=()
|
|
|
|
local libraries=()
|
|
|
|
for flag in $our_flags $flags; do
|
|
|
|
if [[ $flag == -l* ]]; then
|
|
|
|
libraries+=($flag)
|
|
|
|
else
|
|
|
|
final_flags+=($flag)
|
|
|
|
fi
|
|
|
|
done
|
|
|
|
|
|
|
|
echo $compiler $std ${final_flags[@]} $file ${libraries[@]} -o $out >&2
|
|
|
|
$compiler $std ${final_flags[@]} $file ${libraries[@]} -o $out >&2
|
2016-10-18 01:22:46 -07:00
|
|
|
}
|
|
|
|
|
|
|
|
compile "$@"
|