#!/bin/bash
#
# test_disk_space
#
# Schickt belegten Plattenplatz fuer alle lokalen Platten an Loggingdatenbank
# -i: include free inodes
# -m: include tmpfs
# -n: include network mounts (NFS and CIFS)
# -q: send all btrfs quota-groups
# -Q: include snapshots
#
#############################################################################
#
unset TMP_PATH SETULSHOSTNAME SECTION TESTSTEP NFS QA QS CONFIGDIR INODES TMPFS CIFS
while getopts ih:s:t:d:C:T:mnqQ op
 do
  case "$op" in
   i) INODES=1;;
   n) NFS="|:"
      CIFS="|cifs";;
   q) QA=1;;
   Q) QS=1;;
   m) TMPFS="|^tmpfs";;
   C) [[ -n "$OPTARG" ]] && CONFIGDIR="$OPTARG";;
   d) [[ -n "$OPTARG" ]] && TMP_PATH="-d $OPTARG";;
   h) [[ -n "$OPTARG" ]] && SETULSHOSTNAME="$OPTARG";;
   s) [[ -n "$OPTARG" ]] && SECTION="$OPTARG";;
   t) [[ -n "$OPTARG" ]] && TESTSTEP="$OPTARG";;
   T) ;;
   *) echo "usage: `basename $0` [-C <path>] [-d <path>] [-h <ulshostname>] [-s <section>] [-t <teststep>] [-i] [-m] [-n] [-q] [-Q]"
      exit 1;;
  esac
done
shift $(( $OPTIND -1))
#
. `dirname $0`/uls_header
#
DISKS=$(sort /proc/mounts | awk '
($1 ~ "^/dev'$NFS$TMPFS'" || $(NF-3) ~ "btrfs|ext[234]|hfs|ntfs|vfat|xfs|zfs'$CIFS$TMPFS'") && $2 !~ "media" && $(NF-2) ~ "rw" {
      if( !a[$1] && !b[$2] )
      { a[$1] = 1
        b[$2] = 1
        print $2
      }
    }')
if [[ -z "$DISKS" ]]
 then
  DISKS=$(awk '
($1 ~ "^/dev'$NFS$TMPFS'" || $(NF-3) ~ "btrfs|ext[234]|hfs|ntfs|vfat|xfs|zfs'$CIFS$TMPFS'") && $2 !~ "media" && $(NF-2) ~ "rw" {
      if( !a[$1] && !b[$2] )
      { a[$1] = 1
        b[$2] = 1
        print $2
      }
    }' /proc/mounts)
fi
if [[ -n "$DISKS" ]]
 then
  df -mP $DISKS | awk -v H="${SETULSHOSTNAME:-$ULSHOSTNAME}" -v SECTION="${SECTION:-System}" -v TESTSTEP="${TESTSTEP:-Disk Space}" -v DT="$DT" '
BEGIN { print "D;" DT ";" H ";" SECTION ";" }
$5 ~ "[0-9]%" { gsub("%", "", $5)
  if( $2 == 0 )
    f = 0
  else
  { f = 4 - log($2/1024)/2.3
    if( f < 0 )
      f = 0
  }
  printf("V;;;;%s:%s;size;%0.*f;GByte\n", TESTSTEP, $6, f, $2/1024)
  printf("V;;;;;used;%0.*f;GByte\n", f, $3/1024)
  printf("V;;;;;free;%0.*f;GByte\n", f, $4/1024)
  if( $2 > 0 )
    printf("V;;;;;%%used;%.1f;%%\n", 100*(1-$4/$2))
}'
  if which btrfs >/dev/null 2>&1
   then
    for d in $(df -PT $DISKS | awk '$2 == "btrfs" {print $NF}')
     do
      btrfs filesystem usage -b $d | awk -F ':[[:blank:]]*' -v TESTSTEP="${TESTSTEP:-Disk Space}:$d" '
        $1 ~ "Device size$"      { ds = $2 }
        $1 ~ "Device allocated$" { al = $2 }
        END { if( ds > 0 && al > 0 )
                printf("V;;;;%s;Btrfs %%allocated;%.1f;%%\n", TESTSTEP, 100*al/ds)
            }'
    done
  fi
fi | send_test_tab $TMP_PATH
if [[ -n "$INODES" ]]
 then
  DISKS=$(sort /proc/mounts | awk '
$(NF-3) ~ "xfs|ext[234]'$TMPFS'" && $2 !~ "media" {
      if( !a[$1] && !b[$2] )
      { a[$1] = 1
        b[$2] = 1
        print $2
      }
    }')
  if [[ -z "$DISKS" ]]
   then
    DISKS=$(awk '
$(NF-3) ~ "xfs|ext[234]'$TMPFS'" && $2 !~ "media" {
      if( !a[$1] && !b[$2] )
      { a[$1] = 1
        b[$2] = 1
        print $2
      }
    }' /proc/mounts)
  fi
  if [[ -n "$DISKS" ]]
   then
    df -iP $DISKS | awk -v H="${SETULSHOSTNAME:-$ULSHOSTNAME}" -v SECTION="${SECTION:-System}" -v TESTSTEP="${TESTSTEP:-Disk Space}" -v DT="$DT" '
BEGIN { print "D;" DT ";" H ";" SECTION ";" }
$2+0 > 0 {
  printf("V;;;;%s:%s;Ifree;%d;#\n", TESTSTEP, $6, $4)
  printf("V;;;;%s:%s;%%Iused;%.1f;%%\n", TESTSTEP, $6, $3/$2*100)
}' | send_test_tab $TMP_PATH
  fi
fi
#
# btrfs Quotas
if which btrfs >/dev/null 2>&1
 then
  ( echo "D;$DT;${SETULSHOSTNAME:-$ULSHOSTNAME};${SECTION:-System};"
    mount | awk '/^\/dev.* type btrfs/ {if(!a[$1]&&!b[$3]){print $3;a[$1]=1;b[$3]=1}}' | while read m
     do
      export m
      btrfs qgroup show -re --raw "$m" 2>/dev/null | awk -v A=${QA:-0} -v S=${QS:-0} -v "MP=$m" '
BEGIN { c = "btrfs subvolume list " MP
        while( (c | getline) > 0 )
        { if( $NF == "@" )
            mp[$2] = MP
          else
            mp[$2] = MP $NF
        }
        close(c)
        g = 1073741824
      }
$1 ~ "/" && ($4 + $5 > 0 || A || S ) {
      split($1, a, "/")
      r = $2 + 0
      e = $3 + 0
      mr = $4 + 0
      me = $5 + 0
      if( mr > 0 )
      { f = 4 - log(mr/g)/2.3
        if( f < 0 )
          f = 0
        printf("V;;;;QGroups:%s;refer;%0.*f;GByte\n", mp[a[2]], f, r/g)
        printf("V;;;;QGroups:%s;max_refer;%0.*f;GByte\n", mp[a[2]], f, mr/g)
        printf("V;;;;QGroups:%s;free_refer;%0.*f;GByte\n", mp[a[2]], f, (mr-r)/g)
        printf("V;;;;QGroups:%s;%%used_refer;%.1f;%%\n", mp[a[2]], r/mr*100)
        printf("V;;;;QGroups:%s;excl;%0.*f;GByte\n", mp[a[2]], f, e/g)
      }
      else if( me > 0 )
      { f = 4 - log(me/g)/2.3
        if( f < 0 )
          f = 0
        printf("V;;;;QGroups:%s;refer;%0.*f;GByte\n", mp[a[2]], f, r/g)
        printf("V;;;;QGroups:%s;excl;%0.*f;GByte\n", mp[a[2]], f, e/g)
        printf("V;;;;QGroups:%s;max_excl;%0.*f;GByte\n", mp[a[2]], f, me/g)
        printf("V;;;;QGroups:%s;free_excl;%0.*f;GByte\n", mp[a[2]], f, (me-e)/g)
        printf("V;;;;QGroups:%s;%%used_excl;%.1f;%%\n", mp[a[2]], e/me*100)
      }
      else if( mp[a[2]] ~ "/[.]snapshots" )
      { if( S )
        { printf("V;;;;QGroups:%s;refer;%0.*f;GByte\n", mp[a[2]], f, r/g)
          printf("V;;;;QGroups:%s;excl;%0.*f;GByte\n", mp[a[2]], f, e/g)
        }
      }
      else if( A && mp[a[2]] )
      { printf("V;;;;QGroups:%s;refer;%0.*f;GByte\n", mp[a[2]], f, r/g)
        printf("V;;;;QGroups:%s;excl;%0.*f;GByte\n", mp[a[2]], f, e/g)
      }
    }'
    done
  ) | send_test_tab $TMP_PATH
fi
