#!/bin/bash
# mp-shared-objects
# Print path of linked objects and optionally test for their existence on disk.

# Argument = [-q] <path name>

eError="error: no such path"

usage()
{
cat << EOF

usage: $(basename $0) options

This script runs otool -XL over the contents of a path:
\$ $(basename $0) -p /opt/local/lib/mysql5
or a MacPorts port name:
\$ $(basename $0) -p mysql5 -m


OPTIONS:
    -h      Show this message
    -p      Path or Port (requires -m) to check
    -m      Use -p as a port name rather then a path
    -c      Check if shared library exists, print "${eError}" if it does not
    -d      Destroot, prepend -d to -c file check path
    -a      Print arch
    -q      Quiet, only print errors, implies -c
    -s      Stop on errors

EOF
}

[ -z $TYPE ] && TYPE=PATH
[ -z $CHECK_EXISTS ] && CHECK_EXISTS=
[ -z $DESTROOT ] && DESTROOT=
[ -z $PRINT_ARCH ] && PRINT_ARCH=
[ -z $QUIET ] && QUIET=
[ -z $STOP ] && STOP=

while getopts "hp:mcd:qs" OPTION
do
    case $OPTION in
        h)
            usage
            exit 1
            ;;
        p)
            NAME=$OPTARG
            ;;
        m)
            TYPE=PORT
            ;;
        c)
            CHECK_EXISTS=yes
            ;;
        d)
            DESTROOT=$OPTARG
            ;;
        a)
            PRINT_ARCH=yes
            ;;
        q)
            QUIET=yes
            CHECK_EXISTS=yes
            ;;
        s)
            STOP=yes
            ;;
        ?)
            usage
            exit
            ;;
    esac
done

if [[ -z $NAME ]]
then
    usage
    exit 1
fi

IFS=$'\n'
if [ "${TYPE}" == "PATH" ]
then
  FILES=( $(find "${NAME}" -type f) )
fi
if [ "${TYPE}" == "PORT" ]
then
  FILES=( $(port -q contents "${NAME}" | sed -e "s/^ *//") )
fi
for (( fc = 0 ; fc < ${#FILES[@]} ; fc++ ))
do
    if [[ ! -f "${FILES[$fc]}" && ! -d "${FILES[$fc]}" ]]
    then
        echo "FILE ${eError}: ${FILES[$fc]}"
        break 1
    fi
    if [ ! -d "${FILES[$fc]}" ]
    then    
        SHAREDLIBRARIES=( $(otool -XL "${FILES[$fc]}" | sed -e "s/^Archive.*//" | tr -d '\t' | awk '{print $1}') )
        if [[ ${#SHAREDLIBRARIES[@]} -gt 0 ]]
        then
            [ -z $QUIET ] && echo "${FILES[$fc]}"
            [ -z $PRINT_ARCH ] && lipo -info "${FILES[$fc]}"
            for (( sc = 0 ; sc < ${#SHAREDLIBRARIES[@]} ; sc++ ))
            do
                if [[ -f "${SHAREDLIBRARIES[$sc]}" ]]
                then
                    [ -z $QUIET ] && echo -e "\t${SHAREDLIBRARIES[$sc]}"
                    [ -z $PRINT_ARCH ] && lipo -info "${SHAREDLIBRARIES[$sc]}"
                elif [[ ! -z $DESTROOT && -f "${DESTROOT}${SHAREDLIBRARIES[$sc]}" ]]
                then
                    [ -z $QUIET ] && echo -e "\t${DESTROOT}${SHAREDLIBRARIES[$sc]}"
                    [ -z $PRINT_ARCH ] && lipo -info "${DESTROOT}${SHAREDLIBRARIES[$sc]}"
                else
                    [ -n $QUIET ] && echo "${FILE[$fc]}"
                    echo "SHAREDLIBRARY ${eError}: ${SHAREDLIBRARIES[$sc]}"
                    [ "${STOP}" == "yes" ] && break 2
                fi
            done
        fi
    fi
done
unset IFS
unset NAME
unset CHECK_EXISTS
unset PRINT_ARCH
unset QUIET