#!/bin/bash # This really is a bash script, please don't change to #!/bin/sh # TODO: rewrite, this is fugly. Maybe use perl instead of bash. SBOROOT=${SBOROOT:-/home/urchlay/sbogit} if [ ! -d $SBOROOT ]; then SBOROOT=. fi SELF="$( echo "$0" | sed 's,.*/,,' )" usage() { cat <<EOF $SELF: print dependency tree of SBo builds B. Watson, 20210308. Licensed under WTFPL: Do WTF you want with this. Usage: $SELF [-i] [-q] [-t] [package [package ...]] -i Ignore installed packages (treat everything as not installed). -q Output a sbopkg queue file (sqf). With -i, this will be a complete queue, with all deps listed. Without -i, the queue file won't contain packages that are already installed (which might mean no output at all). This is actually the default (-q option not required). -t Output a recursive 'tree' listing of dependencies. This used to be the default. A local copy of the slackbuilds.org repository is required, created with e.g. rsync or 'git clone'. By default, this script assumes the current directory is the repo of the Slackware version you're running, but you can set SBOROOT in the environment to use a different location. Example: export SBOROOT=/home/bob/sbomirror/14.1 The SBOROOT (or current dir) needs to contain the category directories (academic, accessibility, audio, etc etc). EOF } print_installed_status() { if [ "$IGNORE" = "yes" ]; then echo return fi pkg_is_installed $1 >/dev/null && echo " (installed)" || echo " (NOT installed)" } find_deps() { local i local req local REQUIRES local info=$(/bin/ls $SBOROOT/*/$2/$2.info 2>/dev/null | head -1) if [ -z "$info" ]; then echo "$SELF: $2: no such package" 1>&2 RETVAL=1 return; fi eval $(grep ^REQUIRES= $info) if [ "$REQUIRES" = "" ]; then return fi for req in $REQUIRES; do for i in $(seq 1 $1 ); do echo -n " " done echo -n $req if [ "$req" = "%README%" ]; then echo else print_installed_status $req if [ "$QUEUE" = "yes" ]; then if [ "$IGNORE" = "yes" ] || ! pkg_is_installed $req ; then echo $1 $req >> $QTMPFILE fi fi find_deps $(( $1 + 1 )) $req fi done } QUEUE=yes while [ "$argsdone" != "yes" ]; do case "$1" in -h|-help|--help) usage; exit 0 ;; -iq|-qi) QUEUE=yes ; IGNORE=yes ; shift ;; -it|-ti) QUEUE=no ; IGNORE=yes ; shift ;; -t) QUEUE=no ; shift ;; -q) QUEUE=yes ; shift ;; -i) IGNORE=yes ; shift ;; -*) echo "Unknown option $1"; usage; exit 1 ;; *) argsdone=yes ;; esac done if [ "$QUEUE" = "yes" ]; then QTMPFILE=${TMP:-/tmp}/sbodeps.$$.$RANDOM rm -f $QTMPFILE # save old stdout to fd 3, suppress stdout since we don't print our tree exec 3>&1 1>/dev/null fi if [ ! -e "$SBOROOT/system" ]; then echo "$SELF: path \"$SBOROOT\" doesn't look like an SBo repo, set SBOROOT in environment" 1>&2 exit 1 fi RETVAL=0 [ "$1" = "" ] && set "$( basename $( pwd ) )" for arg; do [ "$arg" = "." ] && arg="$( basename $( pwd ) )" echo -n $arg print_installed_status $arg if [ "$QUEUE" = "yes" ]; then if ! pkg_is_installed $arg || [ "$IGNORE" = "yes" ]; then echo 0 $arg >> $QTMPFILE fi fi find_deps 1 $arg done # The queue temp file contains the same info as the regular # tree, though less human-readable (depth numbers instead of indents). # To turn it into a .sqf, sort it depth-first, and remove any duplicates # (can't use sort -u or uniq, as dups might occur at different depths & # thus not be on consecutive lines). if [ "$QUEUE" = "yes" -a -e "$QTMPFILE" ]; then exec 1>&3 # restore old stdout for q in $(sort -nr $QTMPFILE | cut -d' ' -f2); do r=seen_$(echo $q | sed 's,[^A-Za-z0-9_],_,g') s=${!r} # bash indirect variable ref, yay if [ "$s" != "yes" ]; then echo $q eval $r="yes" fi done rm -f $QTMPFILE fi exit $RETVAL