# env/runtime.env — single self-configuring runtime environment for Klammertext. # # Source this from your shell profile (~/.bashrc etc.): # source /path/to/klammertext/K/env/runtime.env # # This is the runtime counterpart of the shared env/makefile.env: one file # for every machine, with all machine-specific values AUTO-DETECTED. There is no # per-host runtime.env. file and no HOST/OS/SITE selector. # - KLAMMERTEXT_HOME : derived from this file's own location (self-locating) # - KLAMMERTEXT_TEXLIVE_BIN : newest ~/external/texlive//bin/ # Machine-unique, non-committable additions (extra library paths such as NVIDIA # iray, local tools, etc.) go in an optional, gitignored env/runtime.env.local # sourced at the end -- NOT in this shared file, so one machine's bundled # libraries can't shadow another's system libraries. # --- KLAMMERTEXT_HOME: self-locate (bash sets BASH_SOURCE; zsh sets $0) -------- # This file lives at $KLAMMERTEXT_HOME/env/runtime.env, so go up one level. _kt_self="${BASH_SOURCE[0]:-$0}" export KLAMMERTEXT_HOME="$(cd "$(dirname "$_kt_self")/.." && pwd)" unset _kt_self _kt_uname="$(uname -s)" # Windows under MSYS2: the commands are native programs and never understand # MSYS's /c/... spelling, so KLAMMERTEXT_HOME and TMPDIR reach them in Windows # form (C:/..., cygpath -m). bash's own PATH keeps the POSIX form -- a colon # inside a PATH entry splits it. Python (python.org's) is the user's to put on # PATH; an MSYS2 login shell does not inherit the Windows PATH by default. _kt_home_posix="$KLAMMERTEXT_HOME" case "$_kt_uname" in MINGW*|MSYS*) export KLAMMERTEXT_HOME="$(cygpath -m "$KLAMMERTEXT_HOME")" export TMPDIR="$(cygpath -m "${TMPDIR:-/tmp}")" export PYTHON="${PYTHON:-python}" # python.org installs no python3 ;; esac # --- KLAMMERTEXT_TEXLIVE_BIN: newest installed TeX Live under ~/external ------- # Klammertext's TeX Live installs are named by 4-digit year (2024, 2025, 2026). # Match only those so unrelated dirs (e.g. a "texlive-2022-min" system install) # are never selected; sort -V then picks the newest year. if [ "$_kt_uname" = "Darwin" ]; then _kt_arch="universal-darwin" elif case "$_kt_uname" in MINGW*|MSYS*) true;; *) false;; esac; then _kt_arch="windows" # TeX Live's bin/windows else _kt_arch="$(uname -m)-linux" # e.g. x86_64-linux fi # Use `find` with a -path pattern, NOT a shell glob: on macOS/zsh an unmatched # glob (no texlive installed) is a hard "no matches found" error, whereas find # just returns nothing. The -path pattern keeps the 4-digit-year restriction. # Windows: a user installs under the Windows home, %USERPROFILE%\external # (MSYS2's $HOME is C:\msys64\home\, which no Windows guide would name). _kt_tlroot="$HOME/external/texlive" case "$_kt_uname" in MINGW*|MSYS*) _kt_tlroot="$(cygpath -u "$USERPROFILE")/external/texlive";; esac _kt_tl="$(find "$_kt_tlroot" -maxdepth 3 -type d \ -path "*/[0-9][0-9][0-9][0-9]/bin/$_kt_arch" 2>/dev/null \ | sort -V | tail -1)" [ -n "$_kt_tl" ] && export KLAMMERTEXT_TEXLIVE_BIN="$_kt_tl" unset _kt_tl _kt_arch _kt_tlroot # --- PATH (TeX Live appended only if one was found) --------------------------- export PATH="$_kt_home_posix/bin:$_kt_home_posix/tst${KLAMMERTEXT_TEXLIVE_BIN:+:$KLAMMERTEXT_TEXLIVE_BIN}:$PATH" unset _kt_home_posix # --- The Python binding (kpy/) ----------------------------------------------- # "import klammertext" with no setup, as the container image already arranges # through its own PYTHONPATH. Prepended, so a source build shadows any other # copy; the module is bound to the Python the library was built against. export PYTHONPATH="$KLAMMERTEXT_HOME/kpy${PYTHONPATH:+:$PYTHONPATH}" # --- Per-platform: LSan suppressions + shared library search path ------------- # The shared library path deliberately includes ONLY Klammertext's own .so dirs, # NOT third-party bundled-library dirs. In particular NVIDIA iray's platforms/ # ships its own libfreetype.so and Qt6; if added here they shadow the system # libraries, and iray's freetype drags in unversioned libharfbuzz.so/libbz2.so # (absent without -dev packages), which breaks `import OpenImageIO` (SKS @image). # Machine-specific library paths (iray included) go in runtime.env.local. if [ "$_kt_uname" = "Darwin" ]; then # macOS: no LD/DYLD_LIBRARY_PATH needed — libklammertext.so is found via the # binaries' @loader_path rpath and document.so is dlopen'd by absolute path. # LeakSanitizer is unsupported on macOS, so LSAN_OPTIONS does not apply. : else # LSan suppressions for unactionable libpython/OpenImageIO leaks (see # lsan.supp). Real leaks in Klammertext code are still reported; no effect # in performance builds (OPTIMIZE=1, which disables ASan). export LSAN_OPTIONS="suppressions=$KLAMMERTEXT_HOME/env/lsan.supp:print_suppressions=0" export LD_LIBRARY_PATH="$KLAMMERTEXT_HOME/mac:$KLAMMERTEXT_HOME/sks/kutil:$KLAMMERTEXT_HOME/sks/document:$KLAMMERTEXT_HOME/doc/handbook${LD_LIBRARY_PATH:+:$LD_LIBRARY_PATH}" fi unset _kt_uname # --- The mdpdf command (Markdown -> PDF; sks/tns/mdpdf.sh) -------------------- # Sourced here rather than left to each user's profile, so the command exists # wherever the rest of the Klammertext environment does. The file defines one # shell function and registers completion for it: POSIX shell, no output, and # harmless in a non-interactive shell. if [ -f "$KLAMMERTEXT_HOME/sks/tns/mdpdf.sh" ]; then . "$KLAMMERTEXT_HOME/sks/tns/mdpdf.sh" fi # --- Optional per-machine escape hatch (gitignored, absent by default) --------- # Use an if-block (not `[ -f ] && .`) so that when the local file is absent this # file's final exit status is 0 -- otherwise `source runtime.env` returns # non-zero, breaking `source runtime.env && ...` and `set -e` callers. if [ -f "$KLAMMERTEXT_HOME/env/runtime.env.local" ]; then . "$KLAMMERTEXT_HOME/env/runtime.env.local" fi