#!/bin/sh # # next 3 lines configured by make dsastats LOGFILE="QUIPULOG" TAILORFILE="QUIPUTAILOR" LOCALORG="QUIPULOCALORG" ETCDIR="QUIPUETCDIR" logfile=$LOGFILE summary="FALSE" while [ $# -gt 0 ] do case $1 in -s|-summary) summary="TRUE"; shift;; *) logfile=$1; shift;; esac done if [ ! -r $logfile ]; then echo "No such file <$logfile>" >&2 exit 1 fi echo "$LOCALORG" |tr "A-Z" "a-z" >/tmp/dsastats$$.localorg # try and sort out the format of the time into something a bit nicer nicetime () { awk ' BEGIN { montharray[1] = "Jan" montharray[2] = "Feb" montharray[3] = "Mar" montharray[4] = "Apr" montharray[5] = "May" montharray[6] = "Jun" montharray[7] = "Jul" montharray[8] = "Aug" montharray[9] = "Sep" montharray[10] = "Oct" montharray[11] = "Nov" montharray[12] = "Dec" } { monthno = substr($0, 1, 2) + 0 dayno = substr($0, 4, 2) time = substr($0, 7, 8) printf("%s on %02d %s", time, dayno, montharray[monthno]) } ' } echo $logfile | grep -s ".usage" if [ "$?" = "0" ]; then dsaname=`basename $logfile .usage` else dsaname=` grep mydsa $TAILORFILE | \ awk -F@ '{split($NF,parts, "=") print parts[2] }' |sed 's/"//g'` fi starttime=`head -1 $logfile | nicetime` endtime=`tail -1 $logfile | nicetime` echo "fordsa $dsaname" >/tmp/dsastats$$.2 echo "starts $starttime" >>/tmp/dsastats$$.2 echo "ends $endtime" >>/tmp/dsastats$$.2 sed 's/[^)]*) //' < $logfile | awk ' BEGIN { gotfirst = "FALSE" } /^(Add|Read|List|Modify|Modifyrdn|Remove|Search|Compare|Getedb) \(.*/ { split ($2,opids,":") lastassoc = opids[1] } { if (gotfirst == "TRUE") { split($0, op, ":") if (op[1] != "DSA control") { print saveline saveline = $0 } else saveline = "DSAControl " lastassoc ": " $(NF-1) " " $(NF) } else { gotfirst = "TRUE" saveline = $0 } } END { print saveline } ' >/tmp/dsastats$$.1 cat $ETCDIR/quipulocaladds /tmp/dsastats$$.1 | awk ' BEGIN { nextdsa = 1; lastcn=0 conns_open["dummy"] = "" locadd["dummy"] = 0 while (getline > 0) { if (substr($0, 1, 1) == "#") break no_localadds++ locadd[no_localadds] = $0 } } /^Bind.*/ { conn_op[$2] = 1 conn [$2 "#" 1] = conn[$2 "#" 1] " " $0 conns_open[$2] = $2 } /^(Add|Read|List|Modify|Modifyrdn|Remove|Search|Compare|Getedb|DSAControl) \(.*/ { split ($2,opids,":") opid = opids[1] conn_op[opid]++ split ($0,oper,":") if (oper[2] == " ") conn [opid "#" conn_op[opid]] = $1 " ROOT" else conn [opid "#" conn_op[opid]] = $1 oper[2] lastcn = opid } /^Unbind.*/ { if (conn[$2 "#" 0] == "") { print conn[$2 "#" 1] if (chain[$2] == 1) print "\tChained " chain[$2] " operation" else print "\tChained " chain[$2] " operations" } else { print conntype[$2] " " conn[$2 "#" 1] for ( i=2; i<= conn_op[$2]; i++) print " " conn[$2 "#" i] } print "" conn_op[$2] = 0 conns_open[$2] = "" } / has started / { for (j in conns_open) { if (conns_open[j] != "") { if (conn[j "#" 0] == "") { print conn[j "#" 1] if (chain[j] == 1) print "\tChained " chain[j] " operation" else print "\tChained " chain[j] " operations" } else { print conntype[j] " " conn[j "#" 1] for (i = 2; i <= conn_op[j]; i++) print " " conn[j "#" i] } print "" conn_op[j] = 0 conns_open[j] = "" } } } /^X500 DAP.*/ { split ($5,opids,":") opid = opids[1] conn_op[opid] = 0 split ($0,oper,":") conn [opid "#" 0] = "from" oper[2] conn [opid "#" 1] = "DAP" conntype [opid] = "remote" y = index($0, ":") thisadd = substr($0, y+1) for (z =1 ; z <= no_localadds; z++) if (substr(thisadd, 2, length(locadd[z])) == locadd[z]) { conntype [opid] = "local" break } } /^QUIPU DSP.*/ { split ($5,opids,":") opid = opids[1] conn_op[opid] = 0 split ($0,oper,":") conn [opid "#" 0] = "Quipu DSP from" oper[2] conn [opid "#" 1] = "QuipuDSP" conntype [opid] = "remote" y = index($0, ":") thisadd = substr($0, y+1) for (z =1 ; z <= no_localadds; z++) if (substr(thisadd, 2, length(locadd[z])) == locadd[z]) { conntype [opid] = "local" break } } /^X500 DSP.*/ { split ($5,opids,":") opid = opids[1] conn_op[opid] = 0 split ($0,oper,":") conn [opid "#" 0] = "from" oper[2] conn [opid "#" 1] = "DSP" conntype [opid] = "remote" y = index($0, ":") thisadd = substr($0, y+1) for (z =1 ; z <= no_localadds; z++) if (substr(thisadd, 2, length(locadd[z])) == locadd[z]) { conntype [opid] = "local" break } } /^DAP Originator.*/ { split ($0,dn,":") if (dn[2] != " ") conn [lastcn "#" conn_op[lastcn]] = conn [lastcn "#" conn_op[lastcn]] "\n\tDAP Originator: " dn[2] else conn [lastcn "#" conn_op[lastcn]] = conn [lastcn "#" conn_op[lastcn]] "\n\tDAP Originator: anonymous" } /^Bound.*/ { split ($6,opids,":") opid = opids[1] conn[opid "#" 0] = "" conn[opid "#" 1] = $0 conn_op[opid] = 1 } /^Chain.*/ { chain[opid]++ } /^Trying.*/ { split ($0,dn,":") if (dsa[dn[2]] == 0) { dsa[dn[2]] = nextdsa dsadn[nextdsa]=dn[2] try[nextdsa]++ nextdsa++ } else try[dsa[dn[2]]]++ } /^Failed.*/ { split ($0,dn,":") fail[dsa[dn[2]]]++ } END { print "Connections: " for (i=1; i< nextdsa; i++) { printf " %-30s: tried %s", dsadn[i], try[i] if (fail[i] != 0) print ", failed " fail[i] else print } } ' >> /tmp/dsastats$$.2 cat /tmp/dsastats$$.localorg $ETCDIR/quiputechusers /tmp/dsastats$$.2 |tr "A-Z" "a-z" | awk ' BEGIN { techies["dummy"] = 0 getline localorg = $0 while (getline > 0) { if (substr($0, 1, 1) == "#") break no_techs++ techies[$0] = 0 } gotdspbind = "FALSE" userorgnames["dummy"] = 0 originators["dummy"] = 0 realaccessed["dummy"] = 0 sysaccessed["dummy"] = 0 summary = "'$summary'" } /^fordsa/ { dsaname = substr($0, 8, length($0)-8+1) } /^starts/ { starttime = substr($0, 8, 40) } /^ends/ { endtime = substr($0, 8, 40) } # add any originators from last DSP connection examined to usernames array / bind/ { if (gotdspbind == "TRUE") for (origuser in originators) if (originators[origuser] != 0) { usernames[origuser]++ if (origuser == "anonymous") if (remote == "TRUE") remoteanon++ else localanon++ originators[origuser] = 0 } if (substr($0, 1, 6) == "remote") remote = "TRUE" else remote = "FALSE" } /.* bind.*\(anonymous\).*/ { if (substr($0, 1, 6) == "remote") remoteanon++ else localanon++ if ($2 == "dap") gotdspbind = "FALSE" else gotdspbind = "TRUE" usernames["anonymous"]++ } /.* bind.*\(no auth\).*/ { if (substr($0, 1, 6) == "remote") if ($2 == "dap") remotenoauthdap++ else remotenoauthdsp++ else if ($2 == "dap") localnoauthdap++ else localnoauthdsp++ } /.* bind.*\(simple\).*/ { if (substr($0, 1, 6) == "remote") remotesimple++ else localsimple++ } / bind.*\(no auth\)| bind.*\(simple\)/ { n = index($0, ":") username = substr($0, n+2) if ($2 == "dap") { gotdspbind = "FALSE" usernames[username]++ } else gotdspbind = "TRUE" } #/dap originator:/ { # n = index($0, ":") # username = substr($0, n+3) # if (username != "anonymous") # originators[username]++ #} /^ getedb/ { getedb++ } /^ modifyrdn / { modifyrdnops++ opDN = substr($0, 13) } /^ add/ { addops++ opDN = substr($0, 7) } /^ modify / { modifyops++ opDN = substr($0, 10) } /^ search/ { searchops++ opDN = substr($0, 10) } /^ list/ { listops++ opDN = substr($0, 8) } /^ read/ { readops++ opDN = substr($0, 8) } /^ read|^ list|^ search|^ modify|^ add/ { n = split(opDN, RDNparts, "@") if (substr(RDNparts[n], 1, 2) == "cn") if (($1 == "read") && (n < 3)) #reading a DSA entry { dsaread++ next } else { opDN = RDNparts[1] for (i = 2; i < n-1; i++) opDN = opDN "@" RDNparts[i] } # was this a system or real use? if (gotdspbind == "TRUE") { # get the originator getline n = index($0, ":") origname = substr($0, n+3) if (origname == username) { spotshadows++ next } else originators[origname]++ } else origname = username techfound = "false" for (techperson in techies) if (techperson == origname) { techfound = "true" break } if (techfound == "true") sysaccessed[opDN]++ else realaccessed[opDN]++ } END { # pick up any last dsp originators if (gotdspbind == "TRUE") for (origuser in originators) if (originators[origuser] != 0) { usernames[origuser]++ if (origuser == "anonymous") if (remote == "TRUE") remoteanon++ else localanon++ originators[origuser] = 0 } printf "Summary of calls to DSA <%s>\nFrom %s to %s\n\n", dsaname, \ starttime, endtime printf "%-30s%8s%8s\n\n", "No. of binds", "local", "remote" printf "%-20s%10s%8d%8d\n", "Anonymous", "", localanon, remoteanon printf "%-20s%10s%8d%8d\n", "Unauth name DAP", "", localnoauthdap, remotenoauthdap printf "%-20s%10s%8d%8d\n", "Unauth name DSP", "",localnoauthdsp, remotenoauthdsp printf "%-20s%10s%8d%8d\n", "Simple", "", localsimple, remotesimple #print "have this list of users" #for (user in usernames) # print user " " usernames[user] #print "" for (user in usernames) { techfound = "false" for (techperson in techies) if (techperson == user) { techfound = "true" break } if (techfound == "true") techbinds += usernames[user] else { n = split(user, RDNparts, "@") if (n == 1) userorg = user else userorg = RDNparts[1] ", " RDNparts[2] orgfound = "false" for (org in userorgnames) if (org == userorg) { orgfound = "true" break } if (orgfound == "false") nontech++ userorgnames[userorg]++ userorgbinds[userorg] += usernames[user] } } printf "\nSystem usage (calls received)\n\n" printf "%-38s%8d\n", "Binds by Directory technicians", techbinds printf "%-38s%8d\n", "Reads of DSA entries", dsaread printf "%-38s%8d\n", "Getedb operations", getedb printf "%-38s%8d\n", "Spot shadows", spotshadows printf "\nWho has used the directory?\n" printf "*Real* usage by organisation\n" printf "%9s%10s\n", "No. users", "No. binds" for (name in userorgnames) if (userorgnames[name] != 0) printf "%9d%10d %s\n", userorgnames[name], userorgbinds[name], name printf "\nWhich parts of the Directory have been accessed - real usage?\n" printf "%s %s\n", "No. ops", "Subtree" printf "Local subtree\n" if (realaccessed[localorg] != 0) { printf "%7d %s\n", realaccessed[localorg], localorg realaccessed[localorg] = 0 } n = 0 for (dn in realaccessed) if ((realaccessed[dn] != 0) && \ (substr(dn, 1, length(localorg)) == localorg)) { n++ sortarray[n] = dn } m = n for (i = 1; i