Mon, 28 Jan 2013 17:37:18 +0100
Correct socket error reporting improvement with IPv6 portable code,
after helpful recommendation by Saúl Ibarra Corretgé on OSips devlist.
michael@13 | 1 | #!@l_prefix@/lib/openpkg/bash |
michael@13 | 2 | ## |
michael@13 | 3 | ## openpkg -- OpenPKG Tool Chain |
michael@428 | 4 | ## Copyright (c) 2000-2012 OpenPKG GmbH <http://openpkg.com/> |
michael@13 | 5 | ## |
michael@428 | 6 | ## This software is property of the OpenPKG GmbH, DE MUC HRB 160208. |
michael@428 | 7 | ## All rights reserved. Licenses which grant limited permission to use, |
michael@428 | 8 | ## copy, modify and distribute this software are available from the |
michael@428 | 9 | ## OpenPKG GmbH. |
michael@13 | 10 | ## |
michael@428 | 11 | ## THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESSED OR IMPLIED |
michael@13 | 12 | ## WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF |
michael@13 | 13 | ## MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. |
michael@13 | 14 | ## IN NO EVENT SHALL THE AUTHORS AND COPYRIGHT HOLDERS AND THEIR |
michael@13 | 15 | ## CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, |
michael@13 | 16 | ## SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT |
michael@13 | 17 | ## LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF |
michael@13 | 18 | ## USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND |
michael@13 | 19 | ## ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, |
michael@13 | 20 | ## OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT |
michael@13 | 21 | ## OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF |
michael@13 | 22 | ## SUCH DAMAGE. |
michael@13 | 23 | ## |
michael@13 | 24 | ## openpkg.sh: Execution Frontend (Language: Bourne-Shell) |
michael@13 | 25 | ## |
michael@13 | 26 | |
michael@13 | 27 | ## |
michael@13 | 28 | ## command line parsing |
michael@13 | 29 | ## |
michael@13 | 30 | |
michael@13 | 31 | # command line options defaults |
michael@13 | 32 | opt_prefix="" |
michael@13 | 33 | opt_tools="" |
michael@13 | 34 | opt_version=no |
michael@13 | 35 | opt_help=no |
michael@13 | 36 | |
michael@13 | 37 | # process command line options by iterating over arguments |
michael@13 | 38 | for opt |
michael@13 | 39 | do |
michael@13 | 40 | case "${opt}" in |
michael@13 | 41 | -*=*) arg=`echo "${opt}" | sed 's/^[-_a-zA-Z0-9]*=//'` ;; |
michael@13 | 42 | *) arg='' ;; |
michael@13 | 43 | esac |
michael@13 | 44 | case "${opt}" in |
michael@13 | 45 | -v|--version ) opt_version=yes; shift ;; |
michael@13 | 46 | -h|--help ) opt_help=yes; shift ;; |
michael@13 | 47 | --prefix=* ) opt_prefix="${arg}"; shift ;; |
michael@13 | 48 | --tools=* ) opt_tools="${arg}"; shift ;; |
michael@13 | 49 | -* ) echo "openpkg:ERROR: Invalid command-line option \"${opt}\"." 1>&2 |
michael@13 | 50 | echo "openpkg:ERROR: Run \"${0} --help\" for list of valid options" 1>&2; exit 1 ;; |
michael@13 | 51 | * ) break ;; |
michael@13 | 52 | esac |
michael@13 | 53 | done |
michael@13 | 54 | |
michael@13 | 55 | ## |
michael@13 | 56 | ## determine OpenPKG locations |
michael@13 | 57 | ## |
michael@13 | 58 | |
michael@13 | 59 | # determine path to OpenPKG instance |
michael@13 | 60 | openpkg_prefix="@l_prefix@" |
michael@13 | 61 | if [ ".${OPENPKG_PREFIX}" != . ]; then |
michael@13 | 62 | openpkg_prefix="${OPENPKG_PREFIX}" |
michael@13 | 63 | fi |
michael@13 | 64 | if [ ".${opt_prefix}" != . ]; then |
michael@13 | 65 | openpkg_prefix="${opt_prefix}" |
michael@13 | 66 | fi |
michael@13 | 67 | if [ -x "${openpkg_prefix}/bin/openpkg" -a -x "${openpkg_prefix}/libexec/openpkg/rpm" ]; then |
michael@13 | 68 | # OpenPKG 2.0 and higher |
michael@13 | 69 | true |
michael@13 | 70 | elif [ -f "${openpkg_prefix}/bin/rpm" -a -x "${openpkg_prefix}/lib/openpkg/rpm" ]; then |
michael@13 | 71 | # OpenPKG 1.x |
michael@13 | 72 | echo "openpkg:ERROR: OpenPKG 1.x instance found under \"${openpkg_prefix}\" (not supported)" 1>&2 |
michael@13 | 73 | exit 1 |
michael@13 | 74 | else |
michael@13 | 75 | echo "openpkg:ERROR: no OpenPKG instance found under \"${openpkg_prefix}\"" 1>&2 |
michael@13 | 76 | exit 1 |
michael@13 | 77 | fi |
michael@13 | 78 | |
michael@13 | 79 | # allow convenient all-in-one specification of OpenPKG Tool Chain locations |
michael@13 | 80 | # (assuming the filesystem layout of an uninstalled OpenPKG Tool Chain) |
michael@13 | 81 | openpkg_tools="${OPENPKG_TOOLS}" |
michael@13 | 82 | openpkg_tools_cmdpath="${OPENPKG_TOOLS_CMDPATH}" |
michael@13 | 83 | openpkg_tools_apipath="${OPENPKG_TOOLS_APIPATH}" |
michael@13 | 84 | if [ ".${opt_tool}" != . ]; then |
michael@13 | 85 | openpkg_tools="${opt_tools}" |
michael@13 | 86 | fi |
michael@13 | 87 | if [ ".${openpkg_tools}" != . -a ".${openpkg_tools_cmdpath}" = . ]; then |
michael@13 | 88 | openpkg_tools_cmdpath="${openpkg_tools}/cmd:@" |
michael@13 | 89 | fi |
michael@13 | 90 | if [ ".${openpkg_tools}" != . -a ".${openpkg_tools_apipath}" = . ]; then |
michael@13 | 91 | openpkg_tools_apipath="${openpkg_tools}/api:@" |
michael@13 | 92 | fi |
michael@13 | 93 | |
michael@13 | 94 | # determine path to OpenPKG Tool Chain commands |
michael@13 | 95 | cmdpath="${openpkg_prefix}/libexec/openpkg" |
michael@428 | 96 | if [ -d "${openpkg_prefix}/libexec/openpkg-bf" ]; then |
michael@428 | 97 | # openpkg-bf package overrides |
michael@428 | 98 | cmdpath="${openpkg_prefix}/libexec/openpkg-bf:${cmdpath}" |
michael@13 | 99 | fi |
michael@428 | 100 | if [ -d "${openpkg_prefix}/libexec/openpkg-rg" ]; then |
michael@428 | 101 | # openpkg-rg package overrides |
michael@428 | 102 | cmdpath="${openpkg_prefix}/libexec/openpkg-rg:${cmdpath}" |
michael@13 | 103 | fi |
michael@13 | 104 | if [ ".${openpkg_tools_cmdpath}" != . ]; then |
michael@13 | 105 | # user supplied path overrides |
michael@13 | 106 | cmdpath=`echo "${openpkg_tools_cmdpath}" | sed -e "s;@;${cmdpath};"` |
michael@13 | 107 | fi |
michael@13 | 108 | openpkg_tools_cmdpath=`echo "${cmdpath}" | sed -e 's/::/:/g' -e 's/^://' -e 's/:$//'` |
michael@13 | 109 | |
michael@13 | 110 | # determine path to OpenPKG Tool Chain API |
michael@13 | 111 | apipath="" |
michael@428 | 112 | if [ -d "${openpkg_prefix}/lib/openpkg-bf" ]; then |
michael@428 | 113 | # openpkg-bf package overrides |
michael@428 | 114 | apipath="${openpkg_prefix}/lib/openpkg-bf:${apipath}" |
michael@428 | 115 | fi |
michael@428 | 116 | if [ -d "${openpkg_prefix}/lib/openpkg-rg" ]; then |
michael@428 | 117 | # openpkg-rg package overrides |
michael@428 | 118 | apipath="${openpkg_prefix}/lib/openpkg-rg:${apipath}" |
michael@13 | 119 | fi |
michael@13 | 120 | if [ ".${openpkg_tools_apipath}" != . ]; then |
michael@13 | 121 | # user supplied path overrides |
michael@13 | 122 | apipath=`echo "${openpkg_tools_apipath}" | sed -e "s;@;${apipath};"` |
michael@13 | 123 | fi |
michael@13 | 124 | openpkg_tools_apipath=`echo "${apipath}" | sed -e 's/::/:/g' -e 's/^://' -e 's/:$//'` |
michael@13 | 125 | |
michael@13 | 126 | ## |
michael@13 | 127 | ## execute stand-alone option commands in advance |
michael@13 | 128 | ## |
michael@13 | 129 | |
michael@13 | 130 | # implement stand-alone "--help" option |
michael@13 | 131 | if [ ".${opt_help}" = .yes ]; then |
michael@13 | 132 | release=`${openpkg_prefix}/libexec/openpkg/rpm --eval '%{l_openpkg_release}'` |
michael@13 | 133 | echo "" |
michael@13 | 134 | echo "This is ${release} <http://www.openpkg.org/>" |
michael@13 | 135 | echo "Cross-Platform Unix Software Packaging Facility" |
michael@13 | 136 | echo "" |
michael@428 | 137 | echo "Copyright (c) 2000-2012 OpenPKG GmbH <http://openpkg.com/>" |
michael@13 | 138 | echo "" |
michael@13 | 139 | echo "The command \"${openpkg_prefix}/bin/openpkg\" is the official command-line" |
michael@13 | 140 | echo "execution frontend of the OpenPKG tool chain. Its usage is:" |
michael@13 | 141 | echo "" |
michael@13 | 142 | echo " \$ ${openpkg_prefix}/bin/openpkg [<option> ...] \\" |
michael@13 | 143 | echo " <command> [<command-option> ...] [<command-argument> ...]" |
michael@13 | 144 | echo "" |
michael@13 | 145 | echo "where <option> is one of the following global options:" |
michael@13 | 146 | echo " -p, --prefix sets the OpenPKG instance prefix (also: \${OPENPKG_PREFIX})" |
michael@13 | 147 | echo " -t, --tools sets the OpenPKG tool chain prefix (also: \${OPENPKG_TOOLS})" |
michael@13 | 148 | echo " -v, --version display OpenPKG version/release" |
michael@13 | 149 | echo " -h, --help display this usage help message" |
michael@13 | 150 | echo "" |
michael@13 | 151 | echo "where <command> is one of the following commands:" |
michael@13 | 152 | echo " rpm (provided by bootstrap package)" |
michael@428 | 153 | echo " rpmcache (provided by bootstrap package)" |
michael@428 | 154 | echo " rpmconstant (provided by bootstrap package)" |
michael@428 | 155 | echo " rpmgrep (provided by bootstrap package)" |
michael@13 | 156 | echo " rpm2cpio (provided by bootstrap package)" |
michael@13 | 157 | echo " rpm-config (provided by bootstrap package)" |
michael@428 | 158 | echo " build (provided by bootstrap package)" |
michael@428 | 159 | echo " curl (provided by bootstrap package)" |
michael@428 | 160 | echo " dev (provided by bootstrap package)" |
michael@428 | 161 | echo " index (provided by bootstrap package)" |
michael@428 | 162 | echo " license (provided by bootstrap package)" |
michael@428 | 163 | echo " lint-fsl (provided by bootstrap package)" |
michael@428 | 164 | echo " lint-rc (provided by bootstrap package)" |
michael@428 | 165 | echo " lint-rpm (provided by bootstrap package)" |
michael@428 | 166 | echo " lint-spec (provided by bootstrap package)" |
michael@428 | 167 | echo " lsync (provided by bootstrap package)" |
michael@428 | 168 | echo " makeproxy (provided by bootstrap package)" |
michael@428 | 169 | echo " man (provided by bootstrap package)" |
michael@428 | 170 | echo " rc (provided by bootstrap package)" |
michael@428 | 171 | echo " register (provided by bootstrap package)" |
michael@428 | 172 | echo " release (provided by bootstrap package)" |
michael@428 | 173 | echo " svs (provided by bootstrap package)" |
michael@13 | 174 | echo " uuid (provided by bootstrap package)" |
michael@428 | 175 | |
michael@13 | 176 | # install command intentionally left out in above display! |
michael@13 | 177 | |
michael@13 | 178 | # dynamically figure out add-on commands |
michael@13 | 179 | for cmd in rpm rpmbuild rpm2cpio rpm-config uuid rc lsync man install; do |
michael@13 | 180 | id=`echo "${cmd}" | sed -e 's/-/_/g'` |
michael@13 | 181 | eval "__cmd_seen_${id}=yes" |
michael@13 | 182 | done |
michael@13 | 183 | OIFS="${IFS}"; IFS=":" |
michael@13 | 184 | for dir in ${openpkg_tools_cmdpath}; do |
michael@13 | 185 | IFS="${OIFS}" |
michael@13 | 186 | if [ ! -d ${dir} ]; then |
michael@13 | 187 | continue |
michael@13 | 188 | fi |
michael@13 | 189 | for cmd in `cd ${dir} 2>/dev/null && echo *`; do |
michael@13 | 190 | name=`echo "${cmd}" | sed -e 's/\.sh$//' -e 's/\.pl$//' \ |
michael@13 | 191 | -e 's/^/X/' -e 's/^X\([a-z][a-zA-Z0-9_-]*\)$/\1/' -e 's/^X.*$//'` |
michael@13 | 192 | if [ ".${name}" != . ]; then |
michael@13 | 193 | if [ -f ${dir}/${cmd} ]; then |
michael@13 | 194 | id=`echo "${name}" | sed -e 's/-/_/g'` |
michael@13 | 195 | eval "seen=\$__cmd_seen_${id}" |
michael@13 | 196 | if [ ".${seen}" != .yes ]; then |
michael@13 | 197 | echo "${name}" | awk '{ printf(" %-15s (provided by add-on package)\n", $0); }' |
michael@13 | 198 | eval "__cmd_seen_${id}=yes" |
michael@13 | 199 | fi |
michael@13 | 200 | fi |
michael@13 | 201 | fi |
michael@13 | 202 | done |
michael@13 | 203 | done |
michael@13 | 204 | IFS="${OIFS}" |
michael@13 | 205 | echo "" |
michael@13 | 206 | echo "where <command-option> and <command-argument> are <command> specific" |
michael@13 | 207 | echo "options and arguments. Run \"${openpkg_prefix}/bin/openpkg <command> --help\"" |
michael@13 | 208 | echo "and \"${openpkg_prefix}/bin/openpkg man <command>\" for more details." |
michael@13 | 209 | echo "" |
michael@13 | 210 | exit 0 |
michael@13 | 211 | fi |
michael@13 | 212 | |
michael@13 | 213 | # implement stand-alone "--version" option |
michael@13 | 214 | if [ ".${opt_version}" = .yes ]; then |
michael@13 | 215 | release=`${openpkg_prefix}/libexec/openpkg/rpm --eval '%{l_openpkg_release}'` |
michael@13 | 216 | version=`${openpkg_prefix}/libexec/openpkg/rpm -q --qf '%{version}' openpkg` |
michael@13 | 217 | echo "${release} (${version})" |
michael@13 | 218 | exit 0 |
michael@13 | 219 | fi |
michael@13 | 220 | |
michael@13 | 221 | ## |
michael@13 | 222 | ## determine command details and execute command appropriately |
michael@13 | 223 | ## |
michael@13 | 224 | |
michael@13 | 225 | # command line sanity check |
michael@13 | 226 | if [ ${#} -eq 0 ]; then |
michael@13 | 227 | echo "openpkg:ERROR: Invalid command-line arguments." 1>&2 |
michael@13 | 228 | echo "openpkg:ERROR: Run \"${openpkg_prefix}/bin/openpkg --help\" for list of valid arguments." 1>&2 |
michael@13 | 229 | exit 1 |
michael@13 | 230 | fi |
michael@13 | 231 | |
michael@13 | 232 | # search command by iterating over all command directories |
michael@13 | 233 | cmd="${1}" |
michael@13 | 234 | shift |
michael@13 | 235 | cmd_path="" |
michael@13 | 236 | cmd_shell="" |
michael@13 | 237 | cmd_stack="${OPENPKG_TOOLS_CMDSTACK}" |
michael@13 | 238 | OIFS="${IFS}"; IFS=":" |
michael@13 | 239 | for dir in ${openpkg_tools_cmdpath}; do |
michael@13 | 240 | IFS="${OIFS}" |
michael@13 | 241 | |
michael@13 | 242 | # skip (currently) not existing directory |
michael@13 | 243 | if [ ! -d ${dir} ]; then |
michael@13 | 244 | continue |
michael@13 | 245 | fi |
michael@13 | 246 | |
michael@13 | 247 | # check for various command implementations |
michael@13 | 248 | if [ -x ${dir}/${cmd} ]; then |
michael@13 | 249 | # found executable stand-alone binary |
michael@13 | 250 | cmd_path="${dir}/${cmd}" |
michael@13 | 251 | cmd_shell="" |
michael@13 | 252 | elif [ -f ${dir}/${cmd}.sh ]; then |
michael@13 | 253 | # found non-executable Bourne-Shell script |
michael@13 | 254 | cmd_path="${dir}/${cmd}.sh" |
michael@13 | 255 | cmd_shell="${openpkg_prefix}/lib/openpkg/bash" |
michael@13 | 256 | elif [ -f ${dir}/${cmd}.pl ]; then |
michael@13 | 257 | # found non-executable Perl script |
michael@13 | 258 | cmd_path="${dir}/${cmd}.pl" |
michael@13 | 259 | if [ -x ${openpkg_prefix}/bin/perl ]; then |
michael@13 | 260 | cmd_shell="${openpkg_prefix}/bin/perl" |
michael@13 | 261 | else |
michael@13 | 262 | cmd_shell=`${openpkg_prefix}/lib/openpkg/shtool path -p "$PATH:$openpkg_prefix/lib/openpkg" -m perl 2>&1` |
michael@13 | 263 | if [ ".${cmd_shell}" = . ]; then |
michael@13 | 264 | echo "openpkg:ERROR: No Perl interpreter found in \${PATH}" 1>&2 |
michael@13 | 265 | exit 1 |
michael@13 | 266 | fi |
michael@13 | 267 | fi |
michael@13 | 268 | # provide Perl module include path(s) to API |
michael@13 | 269 | OIFS="${IFS}"; IFS=":" |
michael@13 | 270 | for dir2 in ${openpkg_tools_apipath}; do |
michael@13 | 271 | IFS="${OIFS}" |
michael@13 | 272 | if [ ! -d ${dir2} ]; then |
michael@13 | 273 | continue |
michael@13 | 274 | fi |
michael@13 | 275 | cmd_shell="${cmd_shell} -I${dir2}" |
michael@13 | 276 | done |
michael@13 | 277 | IFS="${OIFS}" |
michael@13 | 278 | else |
michael@13 | 279 | # command not found, continue searching |
michael@13 | 280 | continue |
michael@13 | 281 | fi |
michael@13 | 282 | |
michael@13 | 283 | # check whether to use this found command or to continue searching |
michael@13 | 284 | # for next command implementation in sequence (in order to support |
michael@13 | 285 | # flexible nested command wrapping) |
michael@13 | 286 | cmd_last=`echo "${cmd_stack}" | sed -e 's;:.*$;;'` |
michael@13 | 287 | if [ ".${cmd_last}" = ".${cmd}" ]; then |
michael@13 | 288 | # we were last command on stack, so pop us from call |
michael@13 | 289 | # stack and continue searching for next implementation |
michael@13 | 290 | cmd_stack=`echo "${cmd_stack}" | sed -e 's;^[^:][^:]*:*;;'` |
michael@13 | 291 | continue |
michael@13 | 292 | else |
michael@13 | 293 | # last command on stack was different, so stop |
michael@13 | 294 | # searching because we found the implementation |
michael@13 | 295 | break |
michael@13 | 296 | fi |
michael@13 | 297 | done |
michael@13 | 298 | IFS="${OIFS}" |
michael@13 | 299 | |
michael@13 | 300 | # sanity check search result |
michael@13 | 301 | if [ ".${cmd_path}" = . ]; then |
michael@13 | 302 | echo "openpkg:ERROR: No such command \"${cmd}\" found in command path" 1>&2 |
michael@13 | 303 | echo "openpkg:ERROR: (${openpkg_tools_cmdpath})." 1>&2 |
michael@13 | 304 | echo "openpkg:ERROR: Set \${OPENPKG_TOOLS_CMDPATH} appropriately." 1>&2 |
michael@13 | 305 | echo "openpkg:ERROR: Run \"${openpkg_prefix}/bin/openpkg --help\" for list of valid commands." 1>&2 |
michael@13 | 306 | exit 1 |
michael@13 | 307 | fi |
michael@13 | 308 | |
michael@13 | 309 | # export essential run-time information to command |
michael@13 | 310 | export OPENPKG_PREFIX="$openpkg_prefix" |
michael@13 | 311 | export OPENPKG_TOOLS_CMDPROG="${0}" |
michael@13 | 312 | export OPENPKG_TOOLS_CMDNAME="${cmd}" |
michael@13 | 313 | export OPENPKG_TOOLS_CMDSTACK=`echo "${OPENPKG_TOOLS_CMDSTACK}" | sed -e 's;^\(.\);:\1;' -e "s;^;${cmd};"` |
michael@13 | 314 | |
michael@13 | 315 | # execute command |
michael@13 | 316 | eval "exec ${cmd_shell} ${cmd_path} \${1+\"\$@\"}" |
michael@13 | 317 |