#!/usr/local/bin/utsm_run
# Start Plasma on the UTSM virtio-gpu 2D device.
# musl busybox.static PUSH-faults at address 0 (leaked SHSTK). Use bash.
# Wayland/KWin DRM does not issue SET_SCANOUT, so the host never sees a
# frame. Xfbdev/Xorg is the path that actually lights scanout; Plasma
# then runs as an X11 client on DISPLAY=:0.
printf '[deshab-kde] interpreter alive inside=pre\n' >/dev/kmsg 2>/dev/null || true
# Persist must not abort the session. Do not remount / rw: that is vdb
# (Arch rootfs) and dirtying it yields ext4 checksum errors.
# Skip the probe when already inside the extra-rootfs chroot.
set +e
INSIDE=0
for arg in "$@"; do
    if [ "$arg" = "--inside" ]; then
        INSIDE=1
    fi
done
if [ "$INSIDE" -eq 0 ] && [ ! -e /etc/deshab-kde-root ]; then
    printf '[deshab-kde] persist: probe\n' >/dev/kmsg 2>/dev/null || true
    grep -E 'persist|vdc' /proc/mounts >/dev/kmsg 2>/dev/null || true
    if [ -x /mnt/persist/usr/bin/startplasma-x11 ] || \
       [ -x /mnt/persist/usr/bin/startplasma-wayland ]; then
        printf '[deshab-kde] persist already has startplasma\n' >/dev/kmsg 2>/dev/null || true
    elif grep -q ' /mnt/persist ' /proc/mounts 2>/dev/null; then
        printf '[deshab-kde] persist mounted but startplasma missing\n' >/dev/kmsg 2>/dev/null || true
    else
        printf '[deshab-kde] remounting /dev/vdc ro on /mnt/persist\n' >/dev/kmsg 2>/dev/null || true
        mkdir -p /mnt/persist 2>/dev/null || true
        mount -t ext4 -o ro,noload /dev/vdc /mnt/persist
        if [ ! -x /mnt/persist/usr/bin/startplasma-x11 ]; then
            src=$(awk '$1 == "/dev/vdc" { print $2; exit }' /proc/mounts)
            if [ -n "$src" ] && [ "$src" != /mnt/persist ]; then
                printf '[deshab-kde] bind %s -> /mnt/persist\n' "$src" >/dev/kmsg 2>/dev/null || true
                mount -o bind "$src" /mnt/persist 2>/dev/null || true
            fi
        fi
        if [ ! -x /mnt/persist/usr/bin/startplasma-x11 ]; then
            printf '[deshab-kde] persist remount failed\n' >/dev/kmsg 2>/dev/null || true
        fi
    fi
    printf '[deshab-kde] persist check done\n' >/dev/kmsg 2>/dev/null || true
fi
set +e

KDE_ROOT="${DESHAB_KDE_ROOT:-/mnt/persist}"
SESSION_USER="${DESHAB_KDE_USER:-deshab}"
SOFTWARE_RENDERING="${DESHAB_KDE_SOFTWARE_RENDERING:-1}"
SEATD_PID=""
XFBDEV_PID=""

printf '[deshab-kde] interpreter alive inside=%s\n' "$INSIDE" > /dev/kmsg 2>/dev/null || true

log() {
    printf '[deshab-kde] %s\n' "$*" >>"$LOG_FILE" 2>/dev/null || true
    printf '[deshab-kde] %s\n' "$*" > /dev/kmsg 2>/dev/null || true
    printf '[deshab-kde] %s\n' "$*" > /dev/console 2>/dev/null || true
    printf '[deshab-kde] %s\n' "$*" >&2
}

# /dev/kmsg drops bursts. Always also hit console via log().
dump_file() {
    local f="$1" max="${2:-40}" n=0
    if [ ! -f "$f" ]; then
        log "missing $f"
        return 1
    fi
    log "file $f bytes=$(wc -c < "$f" 2>/dev/null || echo 0)"
    while IFS= read -r line || [ -n "$line" ]; do
        n=$((n + 1))
        [ "$n" -gt "$max" ] && break
        log "$f:$line"
    done < "$f"
    return 0
}

cleanup_session() {
    set +e
    if [ -n "$SEATD_PID" ]; then
        kill "$SEATD_PID" 2>/dev/null || true
        wait "$SEATD_PID" 2>/dev/null || true
    fi
    if [ -n "$XFBDEV_PID" ]; then
        kill "$XFBDEV_PID" 2>/dev/null || true
        wait "$XFBDEV_PID" 2>/dev/null || true
    fi
    # persist /bin/umount SIGSEGVs in ld.so; overlay is discarded on reboot.
}
trap cleanup_session EXIT INT TERM

start_xfbdev() {
    if [ -S /tmp/.X11-unix/X0 ]; then
        log "X socket already present"
        return 0
    fi
    if ! command -v Xfbdev >/dev/null 2>&1; then
        log "Xfbdev not on guest root; Xorg inside the KDE chroot will be used"
        return 1
    fi
    rm -f /tmp/.X0-lock /tmp/.X11-unix/X0
    mkdir -p /tmp/.X11-unix
    chmod 1777 /tmp /tmp/.X11-unix
    log "starting Xfbdev :0 1024x768"
    Xfbdev :0 -geometry 1024x768 -depth 32 >/dev/null 2>&1 &
    XFBDEV_PID=$!
    i=0
    while [ "$i" -lt 50 ]; do
        if [ -S /tmp/.X11-unix/X0 ]; then
            log "Xfbdev socket ready"
            return 0
        fi
        sleep 0.1
        i=$((i + 1))
    done
    log "WARNING: Xfbdev socket not seen yet, continuing"
    return 0
}

if [ "$INSIDE" -eq 0 ] && [ ! -e /etc/deshab-kde-root ]; then
    LOG_FILE="$KDE_ROOT/var/log/deshab-kde-session.log"
    if [ "$(id -u)" -ne 0 ]; then
        echo "[deshab-kde] ERROR: entering the KDE chroot requires root" >&2
        exit 1
    fi
    printf '[deshab-kde] looking for startplasma in %s\n' "$KDE_ROOT" >/dev/kmsg 2>/dev/null || true
    set +e
    if [ ! -x "$KDE_ROOT/usr/bin/startplasma-x11" ] && \
       [ ! -x "$KDE_ROOT/usr/bin/startplasma-wayland" ]; then
        echo "[deshab-kde] ERROR: no prepared KDE root at $KDE_ROOT" >&2
        printf '[deshab-kde] ERROR: no startplasma at %s\n' "$KDE_ROOT" >/dev/kmsg 2>/dev/null || true
        exit 1
    fi

    # persist ld.so SIGSEGVs at 0 (SHSTK). vdb mount/libmount inodes fail
    # checksum at runtime. Use the static helper that already matches the
    # working daemon toolchain.
    BINDMOUNT=/usr/local/bin/utsm_bindmount
    PERSIST_LD=""
    for ld in \
        "$KDE_ROOT/usr/lib/ld-linux-x86-64.so.2" \
        "$KDE_ROOT/lib64/ld-linux-x86-64.so.2" \
        "$KDE_ROOT/lib/ld-linux-x86-64.so.2"; do
        if [ -x "$ld" ]; then
            PERSIST_LD="$ld"
            break
        fi
    done
    PERSIST_LIBS="$KDE_ROOT/usr/lib:$KDE_ROOT/lib:$KDE_ROOT/usr/lib64"
    kde_mount() {
        if [ -x "$BINDMOUNT" ]; then
            if [ "$1" = --bind ] && [ -n "$2" ] && [ -n "$3" ]; then
                "$BINDMOUNT" bind "$2" "$3"
                return $?
            fi
            if [ "$1" = --make-slave ] && [ -n "$2" ]; then
                "$BINDMOUNT" slave "$2"
                return $?
            fi
            if [ "$1" = -o ] && [ "$2" = bind ] && [ -n "$3" ] && [ -n "$4" ]; then
                "$BINDMOUNT" bind "$3" "$4"
                return $?
            fi
            if [ "$1" = -t ] && [ "$3" = -o ] && [ -n "$5" ] && [ -n "$6" ]; then
                "$BINDMOUNT" fstype "$2" "$5" "$6" "$4"
                return $?
            fi
            if [ "$1" = -t ] && [ -n "$2" ] && [ -n "$3" ] && [ -n "$4" ]; then
                "$BINDMOUNT" fstype "$2" "$3" "$4"
                return $?
            fi
        fi
        /bin/mount "$@"
    }
    log "bindmount=$BINDMOUNT persist_ld=$PERSIST_LD"
    # Do not chmod persist bind targets: overlay copy-up of /dev then
    # makes MS_BIND fail. Do not put vdb /usr/bin first on PATH while
    # LD_LIBRARY_PATH is persist (vdb ls SIGSEGVs in ld.so).

    mkdir -p "$KDE_ROOT/dev" "$KDE_ROOT/proc" "$KDE_ROOT/sys" \
             "$KDE_ROOT/run" "$KDE_ROOT/tmp" "$KDE_ROOT/var/log"
    touch "$LOG_FILE"
    rm -f /tmp/deshab-native
    log "entering KDE root at $KDE_ROOT"
    start_xfbdev || true

    # persist /dev /proc /sys /run are 0555 placeholders. rbind of /dev
    # fails here (stderr is /dev/null from the async daemon). Use bind,
    # chmod first, and keep going with a seeded /dev if needed.
    bind_guest_fs() {
        local name="$1"
        local src="/$name"
        local target="$KDE_ROOT/$name"
        local err=""
        if [ -L "$target" ]; then
            rm -f "$target"
        fi
        mkdir -p "$target" 2>/dev/null || true
        if grep -q " $target " /proc/mounts 2>/dev/null; then
            return 0
        fi
        if [ ! -d "$src" ]; then
            log "WARNING: $src missing"
            return 1
        fi
        err=$(kde_mount --bind "$src" "$target" 2>&1)
        if [ $? -eq 0 ]; then
            kde_mount --make-slave "$target" 2>/dev/null || true
            log "bound $src -> $target"
            return 0
        fi
        err=$(kde_mount -o bind "$src" "$target" 2>&1)
        if [ $? -eq 0 ]; then
            log "bound -o bind $src -> $target"
            return 0
        fi
        log "ERROR: bind $src -> $target failed: $err"
        log "bind diag src=$(ls -ld "$src" 2>/dev/null) tgt=$(ls -ld "$target" 2>/dev/null)"
        return 1
    }

    seed_dev() {
        local target="$KDE_ROOT/dev"
        local n
        mkdir -p "$target"
        chmod 0755 "$target" 2>/dev/null || true
        for n in null zero urandom random tty tty0 console kmsg fb0; do
            if [ -e "/dev/$n" ] && [ ! -e "$target/$n" ]; then
                cp -a "/dev/$n" "$target/$n" 2>/dev/null || true
            fi
        done
        for n in dri input pts shm; do
            if [ -d "/dev/$n" ]; then
                mkdir -p "$target/$n"
                chmod 0755 "$target/$n" 2>/dev/null || true
                if ! grep -q " $target/$n " /proc/mounts 2>/dev/null; then
                    kde_mount --bind "/dev/$n" "$target/$n" 2>/dev/null || \
                        kde_mount -o bind "/dev/$n" "$target/$n" 2>/dev/null || true
                fi
            fi
        done
        if [ ! -d "$target/pts" ]; then
            mkdir -p "$target/pts"
            kde_mount -t devpts devpts "$target/pts" 2>/dev/null || true
        fi
    }

    for fs in dev proc sys; do
        if ! bind_guest_fs "$fs"; then
            if [ "$fs" = dev ]; then
                log "seeding /dev into the KDE root after bind failure"
                seed_dev
            else
                log "ERROR: could not bind /$fs into the KDE root"
                exit 1
            fi
        fi
    done
    # vdb is mounted ro. Binding its /tmp or /run makes those
    # directories read-only, so Xorg cannot create /tmp/.X11-unix
    # and seatd cannot create /run/seatd.sock.
    # BUG-XORG-SEGV 最终方案：不再让 chroot 自启 Xorg（vdb ld.so + persist
    # 库组合在 ld.so 0x15ded NULL+8 segfault，即使换 ld.so/换库集都复现）。
    # 改为把宿主 /tmp、/run bind 进 chroot：native 桌面的 Xorg 套接字
    # /tmp/.X11-unix/X0 与 seatd.sock 直接可见，inner session 检测到
    # socket 已存在就跳过自启 Xorg，Plasma 作为 X11 客户端直连活着的
    # X server（-ac 无鉴权，协议层互通，与 Xorg 的加载器问题无关）。
    for fs in tmp run; do
        mkdir -p "$KDE_ROOT/$fs"
        if kde_mount --bind "/$fs" "$KDE_ROOT/$fs"; then
            log "bound host /$fs -> $KDE_ROOT/$fs"
        elif kde_mount -t tmpfs tmpfs "$KDE_ROOT/$fs"; then
            log "fallback tmpfs on $KDE_ROOT/$fs"
        else
            log "ERROR: mount $KDE_ROOT/$fs failed"
        fi
    done
    chmod 1777 "$KDE_ROOT/tmp" 2>/dev/null || true
    mkdir -p "$KDE_ROOT/tmp/.X11-unix" "$KDE_ROOT/run/user"
    chmod 1777 "$KDE_ROOT/tmp/.X11-unix" 2>/dev/null || true
    if [ -d /dev/pts ] && [ -d "$KDE_ROOT/dev/pts" ] && \
       ! grep -q " $KDE_ROOT/dev/pts " /proc/mounts 2>/dev/null; then
        kde_mount --bind /dev/pts "$KDE_ROOT/dev/pts" 2>/dev/null || \
            kde_mount -t devpts devpts "$KDE_ROOT/dev/pts" 2>/dev/null || true
    fi
    mkdir -p "$KDE_ROOT/home/$SESSION_USER/Desktop"
    mkdir -p /mnt/deshab-esp
    if ! grep -q ' /mnt/deshab-esp ' /proc/mounts 2>/dev/null; then
        if [ -e /dev/disk/by-label/DESHABBOOT ]; then
            kde_mount -t vfat -o rw,utf8,shortname=mixed \
                /dev/disk/by-label/DESHABBOOT /mnt/deshab-esp 2>/dev/null || \
            kde_mount -t vfat -o rw /dev/disk/by-label/DESHABBOOT /mnt/deshab-esp \
                2>/dev/null || true
        fi
        if ! grep -q ' /mnt/deshab-esp ' /proc/mounts 2>/dev/null; then
            for d in /dev/vda1 /dev/sda1 /dev/vda /dev/sda; do
                [ -b "$d" ] || continue
                if kde_mount -t vfat -o rw,utf8,shortname=mixed "$d" /mnt/deshab-esp 2>/dev/null; then
                    break
                fi
            done
        fi
    fi
    if [ -d /mnt/deshab-esp/user/desktop ]; then
        if ! grep -q " $KDE_ROOT/home/$SESSION_USER/Desktop " /proc/mounts 2>/dev/null; then
            kde_mount --bind /mnt/deshab-esp/user/desktop \
                "$KDE_ROOT/home/$SESSION_USER/Desktop" 2>/dev/null || true
        fi
        log "Plasma Desktop bound to ESP user/desktop"
    fi
    if [ ! -d "$KDE_ROOT/home/$SESSION_USER/Desktop" ] || \
       [ -z "$(ls -A "$KDE_ROOT/home/$SESSION_USER/Desktop" 2>/dev/null)" ]; then
        if [ -d /usr/local/share/deshab-desktop ]; then
            cp -a /usr/local/share/deshab-desktop/. \
                "$KDE_ROOT/home/$SESSION_USER/Desktop/" 2>/dev/null || true
        elif [ -d "$KDE_ROOT/usr/local/share/deshab-desktop" ]; then
            cp -a "$KDE_ROOT/usr/local/share/deshab-desktop/." \
                "$KDE_ROOT/home/$SESSION_USER/Desktop/" 2>/dev/null || true
        fi
        log "Plasma Desktop filled from deshab-desktop copy (ESP bind unavailable)"
    fi
    chown -R "$SESSION_USER:$SESSION_USER" \
        "$KDE_ROOT/home/$SESSION_USER/Desktop" 2>/dev/null || true

    set +e
    export DESHAB_KDE_USER="$SESSION_USER"
    export DESHAB_KDE_SOFTWARE_RENDERING="$SOFTWARE_RENDERING"
    export DISPLAY=:0
    export GLIBC_TUNABLES=glibc.cpu.hwcaps=-IBT,-SHSTK,-AVX,-AVX2,-AVX512F
    # persist ld.so SIGSEGVs at NULL+8 (offset 0x15ded) on Xorg/dbus/umount.
    # persist bash survived that loader; other bins did not. Bind vdb's
    # interpreter over persist's so new execs match the working pre-chroot
    # path (vdb ld.so + persist libraries). Do not overlay vdb libc.
    VDB_LD=/lib64/ld-linux-x86-64.so.2
    mkdir -p "$KDE_ROOT/usr/local/bin" "$KDE_ROOT/usr/local/lib"
    if [ -n "$PERSIST_LD" ]; then
        cp -f "$PERSIST_LD" "$KDE_ROOT/usr/local/lib/ld-persist.so" 2>/dev/null || true
        chmod 0755 "$KDE_ROOT/usr/local/lib/ld-persist.so" 2>/dev/null || true
        log "saved persist ld.so to /usr/local/lib/ld-persist.so"
    fi
    if [ -x /usr/local/bin/deshab-kde-session ]; then
        cp -f /usr/local/bin/deshab-kde-session \
            "$KDE_ROOT/usr/local/bin/deshab-kde-session" 2>/dev/null || true
        chmod 0755 "$KDE_ROOT/usr/local/bin/deshab-kde-session" 2>/dev/null || true
        log "copied session onto persist overlay"
    fi
    if [ -x /usr/local/bin/utsm_bindmount ]; then
        cp -f /usr/local/bin/utsm_bindmount \
            "$KDE_ROOT/usr/local/bin/utsm_bindmount" 2>/dev/null || true
        chmod 0755 "$KDE_ROOT/usr/local/bin/utsm_bindmount" 2>/dev/null || true
    fi
    if [ -x /usr/local/bin/utsm_run ]; then
        cp -f /usr/local/bin/utsm_run \
            "$KDE_ROOT/usr/local/bin/utsm_run" 2>/dev/null || true
        chmod 0755 "$KDE_ROOT/usr/local/bin/utsm_run" 2>/dev/null || true
    fi
    if [ -x /usr/local/lib/Xorg.good ]; then
        if kde_mount --bind /usr/local/lib/Xorg.good "$KDE_ROOT/usr/lib/Xorg"; then
            log "bound vdb Xorg.good over persist /usr/lib/Xorg"
        fi
    fi
    if [ -d /usr/local/lib/xorg-libs ]; then
        mkdir -p "$KDE_ROOT/usr/local/lib/xorg-libs"
        if kde_mount --bind /usr/local/lib/xorg-libs "$KDE_ROOT/usr/local/lib/xorg-libs"; then
            log "bound xorg-libs ($(ls /usr/local/lib/xorg-libs | wc -l))"
        fi
    fi
    # plasma-libs: Qt6/KF6 等新增好库。只给 Plasma 的 ldpath 用——Xorg 的
    # 加载环境保持 12:18 验证过的纯 xorg-libs 集（扩大 overlay 会让
    # vdb ld.so 在加载期 segfault，见 /tmp/xorg.err 为空的 rc=139）。
    if [ -d /usr/local/lib/plasma-libs ]; then
        mkdir -p "$KDE_ROOT/usr/local/lib/plasma-libs"
        if kde_mount --bind /usr/local/lib/plasma-libs "$KDE_ROOT/usr/local/lib/plasma-libs"; then
            log "bound plasma-libs ($(ls /usr/local/lib/plasma-libs | wc -l))"
        fi
    fi
    # BUG-XORG-SEGV 根修：persist /usr/lib 有 140 个损坏库（ld.so 解析即
    # NULL+8 segfault）。repair.txt（由注入管线生成）把每个坏实体的好副
    # 本 bind 到 persist 路径上，ld.so 回落解析时命中的也全是好文件。
    if [ -f /usr/local/lib/xorg-libs/repair.txt ] && [ -x "$BINDMOUNT" ]; then
        ok=0; fail=0
        while IFS='|' read -r src dst; do
            [ -z "$src" ] && continue
            # bindmount 在 chroot 外执行：src/dst 都要加 $KDE_ROOT 前缀
            if [ -e "$KDE_ROOT$src" ] && kde_mount --bind "$KDE_ROOT$src" "$KDE_ROOT$dst" 2>/dev/null; then
                ok=$((ok + 1))
            else
                fail=$((fail + 1))
            fi
        done < /usr/local/lib/xorg-libs/repair.txt
        log "persist repair binds: ok=$ok fail=$fail"
    fi
    if [ -f /usr/local/lib/xorg/modules/drivers/modesetting_drv.so ]; then
        mkdir -p "$KDE_ROOT/usr/local/lib/xorg/modules/drivers"
        if kde_mount --bind /usr/local/lib/xorg/modules \
            "$KDE_ROOT/usr/local/lib/xorg/modules"; then
            log "bound xorg modules"
        fi
    fi
    # BUG-XORG-SEGV 复盘：0x15ded 崩点=persist ld.so 已知 bug；12:18 好运行
    # 中 vdb-ld bind 处于激活态（umount EBUSY=未卸载）且 Xorg 存活 → bind
    # 是必需的。之前"过时论"判断有误，恢复默认启用。
    if [ -x "$VDB_LD" ]; then
        for dest in \
            "$KDE_ROOT/lib64/ld-linux-x86-64.so.2" \
            "$KDE_ROOT/usr/lib/ld-linux-x86-64.so.2" \
            "$KDE_ROOT/lib/ld-linux-x86-64.so.2"; do
            [ -e "$dest" ] || [ -L "$dest" ] || continue
            if kde_mount --bind "$VDB_LD" "$dest"; then
                log "bound vdb ld.so over $dest"
            elif cp -f "$VDB_LD" "$dest"; then
                log "copied vdb ld.so over $dest"
            fi
        done
    fi
    # BUG-CHROOT-127: 引导期 chroot 的 persist bash 必须只用 persist 自带
    # 库。宿主侧继承的 LD_LIBRARY_PATH（xorg-libs overlay）会让 chroot 内
    # 加载器优先吃 overlay 库，其中部分与 persist glibc 版本错位 → bash
    # 加载失败 → status 127。Xorg/Plasma 阶段会显式重新设置该变量。
    log "bootstrap ldpath=${LD_LIBRARY_PATH:-unset}"
    unset LD_LIBRARY_PATH
    if [ -x "$KDE_ROOT/usr/bin/bash" ]; then
        log "preflight persist bash"
        "$BINDMOUNT" chroot "$KDE_ROOT" /usr/bin/bash -c \
            'printf "[deshab-kde] persist-bash-ok\n" >/dev/kmsg' || \
            log "WARNING: persist bash preflight failed"
    fi
    if [ -x "$BINDMOUNT" ]; then
        log "chroot via utsm_bindmount bash -c"
        "$BINDMOUNT" chroot "$KDE_ROOT" /usr/bin/bash -c \
            'printf "[deshab-kde] inside-bash\n" >/dev/kmsg; ls -l /usr/local/bin/deshab-kde-session /usr/bin/bash /etc/deshab-kde-root /usr/bin/startplasma-x11 >/dev/kmsg 2>&1; exec /usr/local/bin/deshab-kde-session --inside'
        status=$?
    else
        chroot "$KDE_ROOT" /usr/bin/bash \
            /usr/local/bin/deshab-kde-session --inside
        status=$?
    fi
    set -e
    log "chroot session exited with status $status"
    exit "$status"
fi

LOG_FILE="/var/log/deshab-kde-session.log"
set +e
touch "$LOG_FILE"
export GLIBC_TUNABLES=glibc.cpu.hwcaps=-IBT,-SHSTK,-AVX,-AVX2,-AVX512F
export LIBSEAT_BACKEND=seatd
export XDG_SEAT=seat0
export XDG_VTNR=1
log "inside setup begin"
# Xorg 段错误取证：内核打印 fatal signal 现场（RIP 所在库+偏移），
# 早于 Plasma 阶段的同名设置——Xorg 启动在先。
echo 1 >/proc/sys/kernel/print-fatal-signals 2>/dev/null || true
if ! touch /tmp/.deshab-w 2>/dev/null; then
    log "WARNING: /tmp not writable, mounting tmpfs"
    if [ -x /usr/local/bin/utsm_bindmount ]; then
        /usr/local/bin/utsm_bindmount fstype tmpfs tmpfs /tmp || true
    fi
    mkdir -p /tmp/.X11-unix
    chmod 1777 /tmp /tmp/.X11-unix 2>/dev/null || true
fi
if ! touch /run/.deshab-w 2>/dev/null; then
    log "WARNING: /run not writable, mounting tmpfs"
    if [ -x /usr/local/bin/utsm_bindmount ]; then
        /usr/local/bin/utsm_bindmount fstype tmpfs tmpfs /run || true
    fi
fi
log "tmp_w=$([ -w /tmp ] && echo y || echo n) run_w=$([ -w /run ] && echo y || echo n)"
if [ "$(id -u)" -ne 0 ]; then
    log "ERROR: session setup must start as root"
    exit 1
fi
if ! id "$SESSION_USER" >/dev/null 2>&1; then
    log "ERROR: session user does not exist: $SESSION_USER"
    exit 1
fi
if [ ! -e /dev/dri/card0 ]; then
    log "ERROR: /dev/dri/card0 is unavailable; leaving the fallback console intact"
    exit 1
fi

if [ -w /etc ] || [ -w /etc/machine-id ]; then
    dbus-uuidgen --ensure=/etc/machine-id >/tmp/dbus-uuidgen.out 2>&1 || \
        log "dbus-uuidgen skipped (see /tmp/dbus-uuidgen.out)"
fi
if [ ! -s /etc/machine-id ]; then
    printf '00000000000000000000000000000000\n' >/tmp/machine-id 2>/dev/null || true
    if [ -w /etc ]; then
        cp /tmp/machine-id /etc/machine-id 2>/dev/null || true
    fi
fi
session_uid="$(id -u "$SESSION_USER")"
session_gid="$(id -g "$SESSION_USER")"
runtime_dir="/run/user/$session_uid"
install -d -m 0700 -o "$session_uid" -g "$session_gid" "$runtime_dir"

if command -v seatd >/dev/null 2>&1 && [ ! -S /run/seatd.sock ]; then
    log "starting seatd for the non-systemd guest session"
    seatd -g video >>"$LOG_FILE" 2>&1 &
    SEATD_PID=$!
    s=0
    while [ ! -S /run/seatd.sock ] && [ "$s" -lt 10 ]; do
        if [ -x /usr/local/bin/utsm_bindmount ]; then
            /usr/local/bin/utsm_bindmount msleep 100
        fi
        s=$((s + 1))
    done
fi
log "seatd_sock=$([ -S /run/seatd.sock ] && echo y || echo n) dri=$(ls /dev/dri 2>/dev/null | tr '\n' ' ')"
[ -e /dev/tty0 ] || mknod /dev/tty0 c 4 0 2>/dev/null || true
[ -e /dev/tty1 ] || mknod /dev/tty1 c 4 1 2>/dev/null || true
log "tty=$(ls -l /dev/tty0 /dev/tty1 /dev/console 2>&1 | tr '\n' ' ')"

# BUG-XORG-SEGV: 宿主 /tmp 已 bind 进 chroot（native 桌面的 Xorg 套接字
# 共享可见）。native Xorg 可能比本会话晚一点起来——等待其套接字出现，
# 出现即完全跳过 chroot 自启 Xorg（该路径在 ld.so 0x15ded 必崩）。
if [ ! -S /tmp/.X11-unix/X0 ]; then
    w=0
    while [ ! -S /tmp/.X11-unix/X0 ] && [ "$w" -lt 40 ]; do
        if [ -x /usr/local/bin/utsm_bindmount ]; then
            /usr/local/bin/utsm_bindmount msleep 300
        fi
        w=$((w + 1))
    done
    log "native Xorg socket wait: tries=$w found=$([ -S /tmp/.X11-unix/X0 ] && echo y || echo n)"
fi

if [ ! -S /tmp/.X11-unix/X0 ]; then
    mkdir -p /tmp/.X11-unix /etc/X11
    chmod 1777 /tmp /tmp/.X11-unix
    if command -v Xorg >/dev/null 2>&1; then
        mkdir -p /etc/X11 /tmp /tmp/deshab-xorg-empty
        cat > /tmp/deshab-xorg.conf <<'XORG_EOF'
Section "Files"
    ModulePath "/usr/local/lib/xorg/modules"
    ModulePath "/usr/lib/xorg/modules"
EndSection
Section "ServerLayout"
    Identifier "Layout0"
    Screen 0 "Screen0"
EndSection
Section "ServerFlags"
    Option "AutoAddDevices" "off"
    Option "AutoEnableDevices" "off"
    Option "AutoAddGPU" "false"
    Option "AllowEmptyInput" "on"
    Option "DontVTSwitch" "on"
EndSection
Section "Device"
    Identifier "VirtioGPU"
    Driver "modesetting"
    Option "AccelMethod" "none"
    Option "SWcursor" "on"
    Option "kmsdev" "/dev/dri/card0"
EndSection
Section "Screen"
    Identifier "Screen0"
    Device "VirtioGPU"
    DefaultDepth 24
    SubSection "Display"
        Depth 24
        Modes "1024x768"
    EndSubSection
EndSection
XORG_EOF
        if [ -w /etc/X11 ]; then
            cp /tmp/deshab-xorg.conf /etc/X11/xorg.conf 2>/dev/null || true
        fi
        # /usr/bin/Xorg is a 271-byte sh wrapper that execs suid Xorg.wrap.
        # The wrap exits immediately in this guest. Run the real server.
        # persist /usr/lib/Xorg is 2.6MB but its ELF header is smashed
        # (e_entry=0, 14KB .text). Bind the known-good Arch binary from vdb.
        if [ -x /usr/local/lib/Xorg.good ]; then
            if [ -x /usr/local/bin/utsm_bindmount ]; then
                /usr/local/bin/utsm_bindmount bind /usr/local/lib/Xorg.good \
                    /usr/lib/Xorg >/tmp/xorg.bind 2>&1 || \
                    cp -f /usr/local/lib/Xorg.good /usr/lib/Xorg
            else
                cp -f /usr/local/lib/Xorg.good /usr/lib/Xorg
            fi
            log "using Xorg.good over /usr/lib/Xorg"
        fi
        if [ -x /usr/lib/Xorg ]; then
            XORG_BIN=/usr/lib/Xorg
        elif [ -x /usr/lib/xorg/Xorg ]; then
            XORG_BIN=/usr/lib/xorg/Xorg
        else
            XORG_BIN="$(command -v Xorg)"
        fi
        log "Xorg bin=$XORG_BIN"
        log "drivers=$(ls /usr/lib/xorg/modules/drivers 2>/dev/null | tr '\n' ' ')"
        rm -f /tmp/.X0-lock /tmp/.X11-unix/X0 /tmp/Xorg.0.log /tmp/xorg.er
        # vdb ld.so + persist Xorg SIGSEGVs at Xorg+0 (error 15).
        # Bash is already loaded; drop the vdb interpreter bind so Xorg's
        # PT_INTERP is persist ld.so again. Do not exec ld.so as argv[0].
        XORG_RUN="$XORG_BIN"
        if [ -x /usr/local/bin/utsm_bindmount ]; then
            for p in /lib64/ld-linux-x86-64.so.2 \
                     /usr/lib/ld-linux-x86-64.so.2 \
                     /lib/ld-linux-x86-64.so.2; do
                /usr/local/bin/utsm_bindmount umount "$p" >/tmp/umount.ld 2>&1
                log "umount $p rc=$? $(tr '\n' ' ' < /tmp/umount.ld)"
            done
        fi
        XORG_VT=""
        XORG_IN="/dev/null"
        if [ -e /dev/tty1 ]; then
            XORG_VT=vt1
            XORG_IN=/dev/tty1
        fi
        export LD_LIBRARY_PATH=/usr/local/lib/xorg-libs
        # 取证：ld.so 解析追踪进 stderr（/tmp/xorg.err），崩溃前最后
        # 一个 "file=" 即毒库。内核 fatal-signal 转储已在会话开头打开。
        export LD_DEBUG=libs
        log "ldpath=$LD_LIBRARY_PATH xlibs=$(ls /usr/local/lib/xorg-libs 2>/dev/null | wc -l)"
        log "starting Xorg :0 $XORG_VT bin=$XORG_RUN nsexec"
        if [ -x /usr/local/bin/utsm_bindmount ]; then
            /usr/local/bin/utsm_bindmount nsexec "$XORG_RUN" :0 $XORG_VT \
                -nolisten tcp -noreset -ac -keeptty \
                -novtswitch -sharevts -verbose 6 -logverbose 6 \
                -config /tmp/deshab-xorg.conf \
                -configdir /tmp/deshab-xorg-empty \
                -logfile /tmp/Xorg.0.log \
                <"$XORG_IN" >>/tmp/xorg.err 2>&1 &
        else
            "$XORG_RUN" :0 $XORG_VT -nolisten tcp -noreset -ac -keeptty \
                -novtswitch -sharevts -verbose 6 -logverbose 6 \
                -config /tmp/deshab-xorg.conf \
                -configdir /tmp/deshab-xorg-empty \
                -logfile /tmp/Xorg.0.log \
                <"$XORG_IN" >>/tmp/xorg.err 2>&1 &
        fi
        XFBDEV_PID=$!
        log "Xorg pid=$XFBDEV_PID"
        i=0
        while [ ! -S /tmp/.X11-unix/X0 ] && [ "$i" -lt 20 ]; do
            if [ -x /usr/local/bin/utsm_bindmount ]; then
                /usr/local/bin/utsm_bindmount yield
                /usr/local/bin/utsm_bindmount msleep 200
            fi
            i=$((i + 1))
            alive=n
            [ -n "$XFBDEV_PID" ] && [ -d "/proc/$XFBDEV_PID" ] && alive=y
            if [ "$alive" = n ] || [ $((i % 5)) -eq 0 ]; then
                log "Xorg wait ${i}s socket=$([ -S /tmp/.X11-unix/X0 ] && echo y || echo n) parent=$alive"
            fi
            if [ "$alive" = n ] && [ "$i" -ge 2 ]; then
                wait "$XFBDEV_PID" 2>/dev/null
                log "Xorg parent exited rc=$?"
                break
            fi
        done
        if [ -S /tmp/.X11-unix/X0 ]; then
            log "Xorg socket ready"
        else
            log "WARNING: Xorg socket not ready"
            log "tmp=$(ls -la /tmp /tmp/.X11-unix /var/log 2>&1 | tr '\n' '|')"
            dump_file /tmp/xorg.err 60
            # LD_DEBUG 追踪很长，崩点在末尾——tail 60 行找最后一个 file=
            if [ -x /usr/local/bin/utsm_bindmount ]; then
                /usr/local/bin/utsm_bindmount tail /tmp/xorg.err 60 \
                    > /tmp/xorg.err.tail 2>/dev/null || true
                while IFS= read -r line; do
                    log "xorg.err.tail:$line"
                done < /tmp/xorg.err.tail
            fi
            dump_file /tmp/Xorg.0.log 60
            dump_file /var/log/Xorg.0.log 40
            dump_file "$LOG_FILE" 20
        fi
    else
        log "WARNING: no Xorg/Xfbdev in KDE root"
    fi
fi

if [ ! -S /tmp/.X11-unix/X0 ]; then
    log "ERROR: no X11 socket; not starting Plasma"
    exit 3
fi

log "selecting Plasma launcher"
PLASMA_BIN=""
if [ -x /usr/bin/startplasma-x11 ]; then
    PLASMA_BIN=/usr/bin/startplasma-x11
elif command -v startplasma-x11 >/dev/null 2>&1; then
    PLASMA_BIN="$(command -v startplasma-x11)"
fi

if [ -z "$PLASMA_BIN" ]; then
    log "startplasma-x11 missing; Plasma Wayland will not light virtio-gpu 2D scanout"
    if [ -x /usr/bin/startplasma-wayland ]; then
        PLASMA_BIN=/usr/bin/startplasma-wayland
    fi
fi
if [ -z "$PLASMA_BIN" ]; then
    log "ERROR: no Plasma session binary is installed"
    exit 1
fi

DBUS_LAUNCH=""
if [ -x /usr/lib/plasma-dbus-run-session-if-needed ]; then
    DBUS_LAUNCH=/usr/lib/plasma-dbus-run-session-if-needed
elif command -v dbus-run-session >/dev/null 2>&1; then
    DBUS_LAUNCH="$(command -v dbus-run-session)"
else
    log "ERROR: no Plasma D-Bus session launcher is installed"
    exit 1
fi

if [ "$SOFTWARE_RENDERING" -eq 1 ]; then
    export LIBGL_ALWAYS_SOFTWARE=1
    export GALLIUM_DRIVER=llvmpipe
    export MESA_LOADER_DRIVER_OVERRIDE=llvmpipe
    export QT_QUICK_BACKEND=software
    log "software rendering fallback enabled (llvmpipe/lavapipe)"
fi

export PATH="/usr/local/bin:/usr/bin:/bin:/usr/local/sbin:/usr/sbin:/sbin"
# Plasma 先吃 plasma-libs（Qt6/KF6 好库），再回退 xorg-libs 验证集与 persist。
export LD_LIBRARY_PATH="/usr/local/lib/plasma-libs:/usr/local/lib/xorg-libs${LD_LIBRARY_PATH:+:$LD_LIBRARY_PATH}"
# The Plasma wrapper execs a bare "dbus-run-session". Call it by
# absolute path so a stripped PATH cannot turn into status 127.
# Do not ldd the closure here: that walk hangs this guest and the
# verify marker must mean the child was actually exec'd.
if [ -x /usr/bin/dbus-run-session ]; then
    DBUS_LAUNCH=/usr/bin/dbus-run-session
fi
log "starting Plasma as $SESSION_USER via $PLASMA_BIN DISPLAY=:0"
log "dbus=$DBUS_LAUNCH runuser=/usr/bin/runuser"
echo 1 >/proc/sys/kernel/print-fatal-signals 2>/dev/null || true
set +e
if [ -x /usr/bin/runuser ]; then
    if [ "$DBUS_LAUNCH" = "/usr/lib/plasma-dbus-run-session-if-needed" ]; then
        /usr/bin/runuser --user "$SESSION_USER" -- /usr/bin/env \
            -u DBUS_SESSION_BUS_ADDRESS \
            HOME="/home/$SESSION_USER" \
            USER="$SESSION_USER" \
            LOGNAME="$SESSION_USER" \
            DISPLAY=:0 \
            XDG_RUNTIME_DIR="$runtime_dir" \
            XDG_SESSION_TYPE=x11 \
            XDG_SESSION_CLASS=user \
            XDG_CURRENT_DESKTOP=KDE \
            DESKTOP_SESSION=plasma \
            KDE_FULL_SESSION=true \
            QT_QPA_PLATFORM=xcb \
            LIBSEAT_BACKEND=seatd \
            LD_LIBRARY_PATH="$LD_LIBRARY_PATH" \
            LD_DEBUG=files \
            PATH="$PATH" \
            "$DBUS_LAUNCH" -- "$PLASMA_BIN" >>/tmp/deshab-plasma.err 2>&1
    else
        /usr/bin/runuser --user "$SESSION_USER" -- /usr/bin/env \
            -u DBUS_SESSION_BUS_ADDRESS \
            HOME="/home/$SESSION_USER" \
            USER="$SESSION_USER" \
            LOGNAME="$SESSION_USER" \
            DISPLAY=:0 \
            XDG_RUNTIME_DIR="$runtime_dir" \
            XDG_SESSION_TYPE=x11 \
            XDG_SESSION_CLASS=user \
            XDG_CURRENT_DESKTOP=KDE \
            DESKTOP_SESSION=plasma \
            KDE_FULL_SESSION=true \
            QT_QPA_PLATFORM=xcb \
            LIBSEAT_BACKEND=seatd \
            LD_LIBRARY_PATH="$LD_LIBRARY_PATH" \
            LD_DEBUG=files \
            PATH="$PATH" \
            "$DBUS_LAUNCH" -- "$PLASMA_BIN" >>/tmp/deshab-plasma.err 2>&1
    fi
else
    log "runuser missing; starting Plasma as root so scanout can proceed"
    if [ "$DBUS_LAUNCH" = "/usr/lib/plasma-dbus-run-session-if-needed" ]; then
        /usr/bin/env \
            -u DBUS_SESSION_BUS_ADDRESS \
            HOME=/root \
            USER=root \
            DISPLAY=:0 \
            XDG_RUNTIME_DIR="$runtime_dir" \
            XDG_SESSION_TYPE=x11 \
            XDG_CURRENT_DESKTOP=KDE \
            QT_QPA_PLATFORM=xcb \
            LIBSEAT_BACKEND=seatd \
            LD_LIBRARY_PATH="$LD_LIBRARY_PATH" \
            LD_DEBUG=files \
            PATH="$PATH" \
            "$DBUS_LAUNCH" -- "$PLASMA_BIN" >>/tmp/deshab-plasma.err 2>&1
    else
        /usr/bin/env \
            -u DBUS_SESSION_BUS_ADDRESS \
            HOME=/root \
            USER=root \
            DISPLAY=:0 \
            XDG_RUNTIME_DIR="$runtime_dir" \
            XDG_SESSION_TYPE=x11 \
            XDG_CURRENT_DESKTOP=KDE \
            QT_QPA_PLATFORM=xcb \
            LIBSEAT_BACKEND=seatd \
            LD_LIBRARY_PATH="$LD_LIBRARY_PATH" \
            LD_DEBUG=files \
            PATH="$PATH" \
            "$DBUS_LAUNCH" -- "$PLASMA_BIN" >>/tmp/deshab-plasma.err 2>&1
    fi
fi
status=$?
set -e
if [ "$status" -ne 0 ]; then
    log "Plasma failed with status $status sig=$((status > 128 ? status - 128 : 0))"
    dump_file /tmp/deshab-plasma.err 8
    # The head only shows dbus-run-session warmup. The crash site is at
    # the END of the LD_DEBUG stream; dump the tail so kmsg shows which
    # library/binary was being loaded when the signal hit.
    if [ -x /usr/local/bin/utsm_bindmount ]; then
        /usr/local/bin/utsm_bindmount tail /tmp/deshab-plasma.err 200 \
            > /tmp/deshab-plasma-tail.txt 2>/dev/null || true
        while IFS= read -r line; do
            log "plasma-tail:$line"
        done < /tmp/deshab-plasma-tail.txt
        /usr/local/bin/utsm_bindmount tail /tmp/Xorg.0.log 80 > /tmp/deshab-xorg-tail.txt 2>/dev/null || true
        /usr/local/bin/utsm_bindmount tail /tmp/xorg.err 20 > /tmp/deshab-xorg-err.txt 2>/dev/null || true
        grep -E '\(EE\)|\(WW\)|Fatal|error|failed|Failed' /tmp/deshab-xorg-tail.txt /tmp/deshab-xorg-err.txt 2>/dev/null | head -n 12 | while IFS= read -r line; do
            log "xorg: $line"
        done
    fi
    dmesg 2>/dev/null | tail -n 40 > /tmp/deshab-dmesg.txt || true
    grep -E 'segfault|Bus error|bus error|traps:|EXT4-fs|invalid ELF' /tmp/deshab-dmesg.txt 2>/dev/null | head -n 8 | while IFS= read -r line; do
        log "dmesg: $line"
    done
else
    log "Plasma session ended normally"
fi
exit "$status"
