1*10898Sroland.mainz@nrubsig.org#!/usr/bin/ksh93 2*10898Sroland.mainz@nrubsig.org 3*10898Sroland.mainz@nrubsig.org# 4*10898Sroland.mainz@nrubsig.org# CDDL HEADER START 5*10898Sroland.mainz@nrubsig.org# 6*10898Sroland.mainz@nrubsig.org# The contents of this file are subject to the terms of the 7*10898Sroland.mainz@nrubsig.org# Common Development and Distribution License (the "License"). 8*10898Sroland.mainz@nrubsig.org# You may not use this file except in compliance with the License. 9*10898Sroland.mainz@nrubsig.org# 10*10898Sroland.mainz@nrubsig.org# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 11*10898Sroland.mainz@nrubsig.org# or http://www.opensolaris.org/os/licensing. 12*10898Sroland.mainz@nrubsig.org# See the License for the specific language governing permissions 13*10898Sroland.mainz@nrubsig.org# and limitations under the License. 14*10898Sroland.mainz@nrubsig.org# 15*10898Sroland.mainz@nrubsig.org# When distributing Covered Code, include this CDDL HEADER in each 16*10898Sroland.mainz@nrubsig.org# file and include the License file at usr/src/OPENSOLARIS.LICENSE. 17*10898Sroland.mainz@nrubsig.org# If applicable, add the following below this CDDL HEADER, with the 18*10898Sroland.mainz@nrubsig.org# fields enclosed by brackets "[]" replaced with your own identifying 19*10898Sroland.mainz@nrubsig.org# information: Portions Copyright [yyyy] [name of copyright owner] 20*10898Sroland.mainz@nrubsig.org# 21*10898Sroland.mainz@nrubsig.org# CDDL HEADER END 22*10898Sroland.mainz@nrubsig.org# 23*10898Sroland.mainz@nrubsig.org 24*10898Sroland.mainz@nrubsig.org# 25*10898Sroland.mainz@nrubsig.org# Copyright 2009 Sun Microsystems, Inc. All rights reserved. 26*10898Sroland.mainz@nrubsig.org# Use is subject to license terms. 27*10898Sroland.mainz@nrubsig.org# 28*10898Sroland.mainz@nrubsig.org 29*10898Sroland.mainz@nrubsig.org# 30*10898Sroland.mainz@nrubsig.org# simplefileattributetree1 - build a simple file tree (including file attributes) 31*10898Sroland.mainz@nrubsig.org# 32*10898Sroland.mainz@nrubsig.org 33*10898Sroland.mainz@nrubsig.org# Solaris needs /usr/xpg6/bin:/usr/xpg4/bin because the tools in /usr/bin are not POSIX-conformant 34*10898Sroland.mainz@nrubsig.orgexport PATH=/usr/xpg6/bin:/usr/xpg4/bin:/bin:/usr/bin 35*10898Sroland.mainz@nrubsig.org 36*10898Sroland.mainz@nrubsig.org# Make sure all math stuff runs in the "C" locale to avoid problems 37*10898Sroland.mainz@nrubsig.org# with alternative # radix point representations (e.g. ',' instead of 38*10898Sroland.mainz@nrubsig.org# '.' in de_DE.*-locales). This needs to be set _before_ any 39*10898Sroland.mainz@nrubsig.org# floating-point constants are defined in this script). 40*10898Sroland.mainz@nrubsig.orgif [[ "${LC_ALL}" != "" ]] ; then 41*10898Sroland.mainz@nrubsig.org export \ 42*10898Sroland.mainz@nrubsig.org LC_MONETARY="${LC_ALL}" \ 43*10898Sroland.mainz@nrubsig.org LC_MESSAGES="${LC_ALL}" \ 44*10898Sroland.mainz@nrubsig.org LC_COLLATE="${LC_ALL}" \ 45*10898Sroland.mainz@nrubsig.org LC_CTYPE="${LC_ALL}" 46*10898Sroland.mainz@nrubsig.org unset LC_ALL 47*10898Sroland.mainz@nrubsig.orgfi 48*10898Sroland.mainz@nrubsig.orgexport LC_NUMERIC=C 49*10898Sroland.mainz@nrubsig.org 50*10898Sroland.mainz@nrubsig.org 51*10898Sroland.mainz@nrubsig.orgfunction add_file_to_tree 52*10898Sroland.mainz@nrubsig.org{ 53*10898Sroland.mainz@nrubsig.org typeset treename=$1 54*10898Sroland.mainz@nrubsig.org typeset filename=$2 55*10898Sroland.mainz@nrubsig.org nameref destnodename=$3 56*10898Sroland.mainz@nrubsig.org integer i 57*10898Sroland.mainz@nrubsig.org typeset nodepath # full name of compound variable 58*10898Sroland.mainz@nrubsig.org typeset -a pe # path elements 59*10898Sroland.mainz@nrubsig.org 60*10898Sroland.mainz@nrubsig.org # first built an array containing the names of each path element 61*10898Sroland.mainz@nrubsig.org # (e.g. "foo/var/baz"" results in an array containing "( 'foo' 'bar' 'baz' )") 62*10898Sroland.mainz@nrubsig.org typeset IFS='/' 63*10898Sroland.mainz@nrubsig.org pe+=( ${filename} ) 64*10898Sroland.mainz@nrubsig.org 65*10898Sroland.mainz@nrubsig.org [[ ${pe[0]} == '' ]] && pe[0]='/' 66*10898Sroland.mainz@nrubsig.org 67*10898Sroland.mainz@nrubsig.org # walk path described via the "pe" array and build nodes if 68*10898Sroland.mainz@nrubsig.org # there aren't any nodes yet 69*10898Sroland.mainz@nrubsig.org nodepath="${treename}" 70*10898Sroland.mainz@nrubsig.org for (( i=0 ; i < (${#pe[@]}-1) ; i++ )) ; do 71*10898Sroland.mainz@nrubsig.org nameref x="${nodepath}" 72*10898Sroland.mainz@nrubsig.org [[ ! -v x.node ]] && compound -A x.nodes 73*10898Sroland.mainz@nrubsig.org 74*10898Sroland.mainz@nrubsig.org nodepath+=".nodes[${pe[i]}]" 75*10898Sroland.mainz@nrubsig.org done 76*10898Sroland.mainz@nrubsig.org 77*10898Sroland.mainz@nrubsig.org # insert element 78*10898Sroland.mainz@nrubsig.org nameref node="${nodepath}" 79*10898Sroland.mainz@nrubsig.org [[ ! -v node.elements ]] && compound -A node.elements 80*10898Sroland.mainz@nrubsig.org node.elements[${pe[i]}]=( 81*10898Sroland.mainz@nrubsig.org filepath="${filename}" 82*10898Sroland.mainz@nrubsig.org ) 83*10898Sroland.mainz@nrubsig.org 84*10898Sroland.mainz@nrubsig.org destnodename="${!node}.elements[${pe[i]}]" 85*10898Sroland.mainz@nrubsig.org 86*10898Sroland.mainz@nrubsig.org return 0 87*10898Sroland.mainz@nrubsig.org} 88*10898Sroland.mainz@nrubsig.org 89*10898Sroland.mainz@nrubsig.orgfunction parse_findls 90*10898Sroland.mainz@nrubsig.org{ 91*10898Sroland.mainz@nrubsig.org nameref out=$1 92*10898Sroland.mainz@nrubsig.org typeset str="$2" 93*10898Sroland.mainz@nrubsig.org 94*10898Sroland.mainz@nrubsig.org # find -ls on Solaris uses the following output format by default: 95*10898Sroland.mainz@nrubsig.org #604302 3 -rw-r--r-- 1 test001 users 2678 May 9 00:46 ./httpsresdump 96*10898Sroland.mainz@nrubsig.org 97*10898Sroland.mainz@nrubsig.org integer out.inodenum="${str/~(Elr)[[:space:]]*([[:digit:]]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alpha:]-]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alnum:]]+)[[:space:]]+([[:alnum:]]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alpha:]]*[[:space:]]+[[:digit:]]*[[:space:]]+[[:digit:]:]+)[[:space:]]+(.+)/\1}" 98*10898Sroland.mainz@nrubsig.org integer out.kbblocks="${str/~(Elr)[[:space:]]*([[:digit:]]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alpha:]-]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alnum:]]+)[[:space:]]+([[:alnum:]]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alpha:]]*[[:space:]]+[[:digit:]]*[[:space:]]+[[:digit:]:]+)[[:space:]]+(.+)/\2}" 99*10898Sroland.mainz@nrubsig.org typeset out.mode="${str/~(Elr)[[:space:]]*([[:digit:]]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alpha:]-]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alnum:]]+)[[:space:]]+([[:alnum:]]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alpha:]]*[[:space:]]+[[:digit:]]*[[:space:]]+[[:digit:]:]+)[[:space:]]+(.+)/\3}" 100*10898Sroland.mainz@nrubsig.org integer out.numlinks="${str/~(Elr)[[:space:]]*([[:digit:]]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alpha:]-]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alnum:]]+)[[:space:]]+([[:alnum:]]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alpha:]]*[[:space:]]+[[:digit:]]*[[:space:]]+[[:digit:]:]+)[[:space:]]+(.+)/\4}" 101*10898Sroland.mainz@nrubsig.org compound out.owner=( 102*10898Sroland.mainz@nrubsig.org typeset user="${str/~(Elr)[[:space:]]*([[:digit:]]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alpha:]-]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alnum:]]+)[[:space:]]+([[:alnum:]]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alpha:]]*[[:space:]]+[[:digit:]]*[[:space:]]+[[:digit:]:]+)[[:space:]]+(.+)/\5}" 103*10898Sroland.mainz@nrubsig.org typeset group="${str/~(Elr)[[:space:]]*([[:digit:]]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alpha:]-]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alnum:]]+)[[:space:]]+([[:alnum:]]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alpha:]]*[[:space:]]+[[:digit:]]*[[:space:]]+[[:digit:]:]+)[[:space:]]+(.+)/\6}" 104*10898Sroland.mainz@nrubsig.org ) 105*10898Sroland.mainz@nrubsig.org integer out.filesize="${str/~(Elr)[[:space:]]*([[:digit:]]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alpha:]-]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alnum:]]+)[[:space:]]+([[:alnum:]]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alpha:]]*[[:space:]]+[[:digit:]]*[[:space:]]+[[:digit:]:]+)[[:space:]]+(.+)/\7}" 106*10898Sroland.mainz@nrubsig.org typeset out.date="${str/~(Elr)[[:space:]]*([[:digit:]]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alpha:]-]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alnum:]]+)[[:space:]]+([[:alnum:]]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alpha:]]*[[:space:]]+[[:digit:]]*[[:space:]]+[[:digit:]:]+)[[:space:]]+(.+)/\8}" 107*10898Sroland.mainz@nrubsig.org typeset out.filepath="${str/~(Elr)[[:space:]]*([[:digit:]]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alpha:]-]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alnum:]]+)[[:space:]]+([[:alnum:]]+)[[:space:]]+([[:digit:]]+)[[:space:]]+([[:alpha:]]*[[:space:]]+[[:digit:]]*[[:space:]]+[[:digit:]:]+)[[:space:]]+(.+)/\9}" 108*10898Sroland.mainz@nrubsig.org 109*10898Sroland.mainz@nrubsig.org return 0 110*10898Sroland.mainz@nrubsig.org} 111*10898Sroland.mainz@nrubsig.org 112*10898Sroland.mainz@nrubsig.orgfunction usage 113*10898Sroland.mainz@nrubsig.org{ 114*10898Sroland.mainz@nrubsig.org OPTIND=0 115*10898Sroland.mainz@nrubsig.org getopts -a "${progname}" "${simplefileattributetree1_usage}" OPT '-?' 116*10898Sroland.mainz@nrubsig.org exit 2 117*10898Sroland.mainz@nrubsig.org} 118*10898Sroland.mainz@nrubsig.org 119*10898Sroland.mainz@nrubsig.org# main 120*10898Sroland.mainz@nrubsig.orgbuiltin basename 121*10898Sroland.mainz@nrubsig.orgbuiltin dirname 122*10898Sroland.mainz@nrubsig.org 123*10898Sroland.mainz@nrubsig.orgset -o noglob 124*10898Sroland.mainz@nrubsig.orgset -o nounset 125*10898Sroland.mainz@nrubsig.org 126*10898Sroland.mainz@nrubsig.org# tree base 127*10898Sroland.mainz@nrubsig.orgcompound filetree 128*10898Sroland.mainz@nrubsig.org 129*10898Sroland.mainz@nrubsig.org# benchmark data 130*10898Sroland.mainz@nrubsig.orgcompound bench=( 131*10898Sroland.mainz@nrubsig.org float start 132*10898Sroland.mainz@nrubsig.org float stop 133*10898Sroland.mainz@nrubsig.org) 134*10898Sroland.mainz@nrubsig.org 135*10898Sroland.mainz@nrubsig.orgcompound appconfig=( 136*10898Sroland.mainz@nrubsig.org typeset do_benchmarking=false 137*10898Sroland.mainz@nrubsig.org compound do_record=( 138*10898Sroland.mainz@nrubsig.org typeset content=false 139*10898Sroland.mainz@nrubsig.org typeset filetype=false 140*10898Sroland.mainz@nrubsig.org ) 141*10898Sroland.mainz@nrubsig.org) 142*10898Sroland.mainz@nrubsig.org 143*10898Sroland.mainz@nrubsig.org 144*10898Sroland.mainz@nrubsig.orginteger i 145*10898Sroland.mainz@nrubsig.org 146*10898Sroland.mainz@nrubsig.orgtypeset progname="${ basename "${0}" ; }" 147*10898Sroland.mainz@nrubsig.org 148*10898Sroland.mainz@nrubsig.orgtypeset -r simplefileattributetree1_usage=$'+ 149*10898Sroland.mainz@nrubsig.org[-?\n@(#)\$Id: simplefileattributetree1 (Roland Mainz) 2009-06-26 \$\n] 150*10898Sroland.mainz@nrubsig.org[-author?Roland Mainz <roland.mainz@nrubsig.org>] 151*10898Sroland.mainz@nrubsig.org[+NAME?simplefileattributetree1 - generate compound variable tree which contains file names and their attributes] 152*10898Sroland.mainz@nrubsig.org[+DESCRIPTION?\bsimplefileattributetree1\b is a simple variable tree 153*10898Sroland.mainz@nrubsig.org demo which builds a compound variable tree based on the output 154*10898Sroland.mainz@nrubsig.org of /usr/xpg4/bin/file which contains the file name, the file attributes 155*10898Sroland.mainz@nrubsig.org and optionally file type and content] 156*10898Sroland.mainz@nrubsig.org[b:benchmark?Print time needed to generate the tree.] 157*10898Sroland.mainz@nrubsig.org[c:includecontent?Include the file\'s content in the tree, split into 1kb blocks.] 158*10898Sroland.mainz@nrubsig.org[t:includefiletype?Include the file type (output of /usr/xpg4/bin/file).] 159*10898Sroland.mainz@nrubsig.org 160*10898Sroland.mainz@nrubsig.orgpath 161*10898Sroland.mainz@nrubsig.org 162*10898Sroland.mainz@nrubsig.org[+SEE ALSO?\bksh93\b(1), \bfile\b(1), \bfind\b(1)] 163*10898Sroland.mainz@nrubsig.org' 164*10898Sroland.mainz@nrubsig.org 165*10898Sroland.mainz@nrubsig.orgwhile getopts -a "${progname}" "${simplefileattributetree1_usage}" OPT ; do 166*10898Sroland.mainz@nrubsig.org# printmsg "## OPT=|${OPT}|, OPTARG=|${OPTARG}|" 167*10898Sroland.mainz@nrubsig.org case ${OPT} in 168*10898Sroland.mainz@nrubsig.org b) appconfig.do_benchmarking="true" ;; 169*10898Sroland.mainz@nrubsig.org +b) appconfig.do_benchmarking="false" ;; 170*10898Sroland.mainz@nrubsig.org c) appconfig.do_record.content="true" ;; 171*10898Sroland.mainz@nrubsig.org +c) appconfig.do_record.content="false" ;; 172*10898Sroland.mainz@nrubsig.org t) appconfig.do_record.filetype="true" ;; 173*10898Sroland.mainz@nrubsig.org +t) appconfig.do_record.filetype="false" ;; 174*10898Sroland.mainz@nrubsig.org *) usage ;; 175*10898Sroland.mainz@nrubsig.org esac 176*10898Sroland.mainz@nrubsig.orgdone 177*10898Sroland.mainz@nrubsig.orgshift $((OPTIND-1)) 178*10898Sroland.mainz@nrubsig.org 179*10898Sroland.mainz@nrubsig.org 180*10898Sroland.mainz@nrubsig.org# argument prechecks 181*10898Sroland.mainz@nrubsig.orgif (( $# == 0 )) ; then 182*10898Sroland.mainz@nrubsig.org print -u2 -f "%s: Missing <path> argument.\n" "${progname}" 183*10898Sroland.mainz@nrubsig.org exit 1 184*10898Sroland.mainz@nrubsig.orgfi 185*10898Sroland.mainz@nrubsig.org 186*10898Sroland.mainz@nrubsig.org 187*10898Sroland.mainz@nrubsig.orgprint -u2 -f "# reading file names...\n" 188*10898Sroland.mainz@nrubsig.orgwhile (( $# > 0 )) ; do 189*10898Sroland.mainz@nrubsig.org # "ulimit -c 0" use used to force ksh93 to use a seperate process for subshells, 190*10898Sroland.mainz@nrubsig.org # this is used to work around a bug with LC_ALL changes bleeding through subshells 191*10898Sroland.mainz@nrubsig.org IFS=$'\n' ; typeset -a findls_lines=( $(ulimit -c 0 ; LC_ALL=C find "$1" -type f -ls) ) ; IFS=$' \t\n' 192*10898Sroland.mainz@nrubsig.org shift 193*10898Sroland.mainz@nrubsig.orgdone 194*10898Sroland.mainz@nrubsig.org 195*10898Sroland.mainz@nrubsig.org 196*10898Sroland.mainz@nrubsig.orgprint -u2 -f "# building tree...\n" 197*10898Sroland.mainz@nrubsig.org 198*10898Sroland.mainz@nrubsig.org${appconfig.do_benchmarking} && (( bench.start=SECONDS )) 199*10898Sroland.mainz@nrubsig.org 200*10898Sroland.mainz@nrubsig.orgfor (( i=0 ; i < ${#findls_lines[@]} ; i++ )) ; do 201*10898Sroland.mainz@nrubsig.org compound parseddata 202*10898Sroland.mainz@nrubsig.org typeset treenodename 203*10898Sroland.mainz@nrubsig.org 204*10898Sroland.mainz@nrubsig.org # parse "find -ls" output 205*10898Sroland.mainz@nrubsig.org parse_findls parseddata "${findls_lines[i]}" 206*10898Sroland.mainz@nrubsig.org 207*10898Sroland.mainz@nrubsig.org # add node to tree and return it's absolute name in "treenodename" 208*10898Sroland.mainz@nrubsig.org add_file_to_tree filetree "${parseddata.filepath}" treenodename 209*10898Sroland.mainz@nrubsig.org 210*10898Sroland.mainz@nrubsig.org # merge parsed "find -ls" output into tree node 211*10898Sroland.mainz@nrubsig.org nameref treenode="${treenodename}" 212*10898Sroland.mainz@nrubsig.org treenode+=parseddata 213*10898Sroland.mainz@nrubsig.org 214*10898Sroland.mainz@nrubsig.org # extras (calculated from the existing values in "parseddata") 215*10898Sroland.mainz@nrubsig.org typeset treenode.dirname="${ dirname "${treenode.filepath}" ; }" 216*10898Sroland.mainz@nrubsig.org typeset treenode.basename="${ basename "${treenode.filepath}" ; }" 217*10898Sroland.mainz@nrubsig.org 218*10898Sroland.mainz@nrubsig.org if ${appconfig.do_record.filetype} ; then 219*10898Sroland.mainz@nrubsig.org # Using /usr/(xpg4/)*/bin/file requires a |fork()|+|exec()| which makes the script a few hundred times slower... ;-( 220*10898Sroland.mainz@nrubsig.org typeset treenode.filetype="$(file "${treenode.filepath}")" 221*10898Sroland.mainz@nrubsig.org fi 222*10898Sroland.mainz@nrubsig.org 223*10898Sroland.mainz@nrubsig.org if ${appconfig.do_record.content} ; then 224*10898Sroland.mainz@nrubsig.org if [[ -r "${treenode.filepath}" ]] ; then 225*10898Sroland.mainz@nrubsig.org # We use an array of compound variables here to support 226*10898Sroland.mainz@nrubsig.org # files with holes (and later alternative streams, too) 227*10898Sroland.mainz@nrubsig.org compound -a treenode.content 228*10898Sroland.mainz@nrubsig.org integer cl=0 229*10898Sroland.mainz@nrubsig.org while \ 230*10898Sroland.mainz@nrubsig.org { 231*10898Sroland.mainz@nrubsig.org treenode.content[${cl}]=( 232*10898Sroland.mainz@nrubsig.org typeset type="data" # (todo: "add support for "holes" (sparse files)) 233*10898Sroland.mainz@nrubsig.org typeset -b bin 234*10898Sroland.mainz@nrubsig.org ) 235*10898Sroland.mainz@nrubsig.org read -n1024 treenode.content[${cl}].bin 236*10898Sroland.mainz@nrubsig.org } ; do 237*10898Sroland.mainz@nrubsig.org (( cl++ )) 238*10898Sroland.mainz@nrubsig.org done < "${treenode.filepath}" 239*10898Sroland.mainz@nrubsig.org unset treenode.content[${cl}] 240*10898Sroland.mainz@nrubsig.org 241*10898Sroland.mainz@nrubsig.org typeset -A treenode.hashsum=( 242*10898Sroland.mainz@nrubsig.org [md5]="$(sum -x md5 < "${treenode.filepath}")" 243*10898Sroland.mainz@nrubsig.org [sha512]="$(sum -x sha512 < "${treenode.filepath}")" 244*10898Sroland.mainz@nrubsig.org ) 245*10898Sroland.mainz@nrubsig.org 246*10898Sroland.mainz@nrubsig.org # we do this for internal debugging only 247*10898Sroland.mainz@nrubsig.org if [[ "${ { 248*10898Sroland.mainz@nrubsig.org integer j 249*10898Sroland.mainz@nrubsig.org for (( j=0 ; j < ${#treenode.content[@]} ; j++ )) ; do 250*10898Sroland.mainz@nrubsig.org printf "%B" treenode.content[$j].bin 251*10898Sroland.mainz@nrubsig.org done 252*10898Sroland.mainz@nrubsig.org } | sum -x sha512 ; }" != "${treenode.hashsum[sha512]}" ]] ; then 253*10898Sroland.mainz@nrubsig.org # this should never happen... 254*10898Sroland.mainz@nrubsig.org print -u2 -f "fatal hash mismatch for %s\n" "${treenode.filepath}" 255*10898Sroland.mainz@nrubsig.org unset treenode.content treenode.hashsum 256*10898Sroland.mainz@nrubsig.org fi 257*10898Sroland.mainz@nrubsig.org fi 258*10898Sroland.mainz@nrubsig.org fi 259*10898Sroland.mainz@nrubsig.orgdone 260*10898Sroland.mainz@nrubsig.org 261*10898Sroland.mainz@nrubsig.org${appconfig.do_benchmarking} && (( bench.stop=SECONDS )) 262*10898Sroland.mainz@nrubsig.org 263*10898Sroland.mainz@nrubsig.org 264*10898Sroland.mainz@nrubsig.orgif ${appconfig.do_benchmarking} ; then 265*10898Sroland.mainz@nrubsig.org # print benchmark data 266*10898Sroland.mainz@nrubsig.org print -u2 -f "# time used: %f\n" $((bench.stop - bench.start)) 267*10898Sroland.mainz@nrubsig.orgfi 268*10898Sroland.mainz@nrubsig.org 269*10898Sroland.mainz@nrubsig.org# print variable tree 270*10898Sroland.mainz@nrubsig.orgprint -v filetree 271*10898Sroland.mainz@nrubsig.org 272*10898Sroland.mainz@nrubsig.orgexit 0 273*10898Sroland.mainz@nrubsig.org# EOF. 274