#! /bin/bash

# default libexecdir used to bootstrap scripts
libexecdir=${GLOBUS_LOCATION}/libexec

# load GRIS common code and initialization
. ${libexecdir}/grid-info-common

######################################################################

emit_resource_net_summary_attrs ()
{
if [ ! "X${_mds_want_glue}" = "Xtrue" ]
then
  ${GLOBUS_SH_CAT-cat} <<EOF
${_line_class_av}Mds-Net-Total-count: ${_net_count}
EOF
fi
    i=0
    while [ $i -lt ${_net_count} ]
    do
	eval "iface=\${_net_${i}_name}"
	eval "mtu=\${_net_${i}_mtu}"
	eval "netaddr=\${_net_${i}_netaddr}"
	eval "ipaddr=\${_net_${i}_ipaddr}"
	if [ ! "X${_mds_want_glue}" = "Xtrue" ]
	then
	${GLOBUS_SH_CAT-cat} <<EOF
${_line_class_av}Mds-Net-name: ${iface}
${_line_class_av}Mds-Net-netaddr: ${netaddr}
${_line_class_av}Mds-Net-addr: ${ipaddr}
EOF
	else
	${GLOBUS_SH_CAT-cat} <<EOF
${_line_class_av}NetName: ${iface}
${_line_class_av}NetAddr: ${ipaddr}
EOF
	fi
	i=`${EXPR} $i + 1`
    done
}

emit_resource_net_summary ()
{
    # $1 is dn suffix
    # $2 .. $N are additional object entries
    if [ ! "X${_mds_want_glue}" = "Xtrue" ]
    then
${GLOBUS_SH_CAT-cat} <<EOF
${_line_class_dn}dn: $1
${_line_class_oc}objectclass: MdsNetTotal
${_line_class_oc}objectclass: MdsNet
EOF
else
${GLOBUS_SH_CAT-cat} <<EOF
${_line_class_oc}objectclass: EDTTop
${_line_class_oc}objectclass: ClusterTop
${_line_class_oc}objectclass: Network
EOF
fi
    shift
    while [ $# -gt 0 ]
    do
	${GLOBUS_SH_CAT-cat} <<EOF
$1
EOF
	shift
    done
    emit_resource_net_summary_attrs | sort | uniq
    echo ""
}

emit_resource_net_devices ()
{
    i=0
    while [ $i -lt ${_net_count} ]
    do
	eval "iface=\${_net_${i}_name}"
	eval "mtu=\${_net_${i}_mtu}"
	eval "netaddr=\${_net_${i}_netaddr}"
	eval "ipaddr=\${_net_${i}_ipaddr}"
	if [ ! "X${_mds_want_glue}" = "Xtrue" ]
	then
	${GLOBUS_SH_CAT-cat} <<EOF
${_line_class_dn}dn: Mds-Device-name=${iface}, $1
${_line_class_oc}objectclass: MdsDevice
${_line_class_oc}objectclass: MdsNet
${_line_class_av}Mds-Device-name: ${iface}
${_line_class_av}Mds-Net-name: ${iface}
${_line_class_av}Mds-Net-netaddr: ${netaddr}
${_line_class_av}Mds-Net-addr: ${ipaddr}
EOF
	else
	${GLOBUS_SH_CAT-cat} <<EOF
${_line_class_av}NetName: ${iface}
${_line_class_av}NetAddr: ${ipaddr}
${_line_class_av}NetMTU: ${mtu}
EOF
	fi
	emit_mds_object_timestamps
	echo

	i=`$EXPR $i + 1`
    done
}

emit_resource_net_descriptions ()
{
    probe_mds_object_timestamps

    timestamps=`emit_mds_object_timestamps`

    if [ "X${_dump_host_object}" = "Xtrue" ]
    then
	emit_resource_net_summary "${_suffix}"
    fi

    if [ "X${_dump_devclass_object}" = "Xtrue" ]
    then
	emit_resource_net_summary "Mds-Device-Group-name=networks, ${_suffix}" "${_line_class_oc}objectclass: MdsDeviceGroup" "${_line_class_av}Mds-Device-Group-name: networks" "$timestamps"
    fi

    if [ "X${_dump_dev_objects}" = "Xtrue" ]
    then
	emit_resource_net_devices "Mds-Device-Group-name=networks, ${_suffix}"
    fi
}

bitwise_and ()
{
    # $1 and $2 are integer operands
    op1=$1
    op2=$2
    fac=1
    sum=0
    while [ $op1 -gt 0 ] && [ $op2 -gt 0 ]
    do 
	bit1=`$EXPR $op1 % 2`
	op1=`$EXPR $op1 / 2`
	bit2=`$EXPR $op2 % 2`
	op2=`$EXPR $op2 / 2`
	bit1=`$EXPR $bit1 \& $bit2`
	sum=`$EXPR $sum + $fac \* $bit1`
	fac=`$EXPR $fac \* 2`
    done
    echo "$sum"
}

compute_netaddr ()
{
    # $1 - $4  ipaddr
    # $5 - $8  netmask

    case $5.$6.$7.$8 in
	255.255.255.255) bits=32 dig1=$1 dig2=$2 dig3=$3 dig4=`bitwise_and $4 $8` ;;
	255.255.255.254) bits=31 dig1=$1 dig2=$2 dig3=$3 dig4=`bitwise_and $4 $8` ;;
	255.255.255.252) bits=30 dig1=$1 dig2=$2 dig3=$3 dig4=`bitwise_and $4 $8` ;;
	255.255.255.248) bits=29 dig1=$1 dig2=$2 dig3=$3 dig4=`bitwise_and $4 $8` ;;
	255.255.255.240) bits=28 dig1=$1 dig2=$2 dig3=$3 dig4=`bitwise_and $4 $8` ;;
	255.255.255.224) bits=27 dig1=$1 dig2=$2 dig3=$3 dig4=`bitwise_and $4 $8` ;;
	255.255.255.192) bits=26 dig1=$1 dig2=$2 dig3=$3 dig4=`bitwise_and $4 $8` ;;
	255.255.255.128) bits=25 dig1=$1 dig2=$2 dig3=$3 dig4=`bitwise_and $4 $8` ;;
	255.255.255.0)   bits=24 dig1=$1 dig2=$2 dig3=$3 dig4=`bitwise_and $4 $8` ;;

	255.255.254.0) bits=23 dig1=$1 dig2=$2 dig3=`bitwise_and $3 $7` dig4=0 ;;
	255.255.252.0) bits=22 dig1=$1 dig2=$2 dig3=`bitwise_and $3 $7` dig4=0 ;;
	255.255.248.0) bits=21 dig1=$1 dig2=$2 dig3=`bitwise_and $3 $7` dig4=0 ;;
	255.255.240.0) bits=20 dig1=$1 dig2=$2 dig3=`bitwise_and $3 $7` dig4=0 ;;
	255.255.224.0) bits=19 dig1=$1 dig2=$2 dig3=`bitwise_and $3 $7` dig4=0 ;;
	255.255.192.0) bits=18 dig1=$1 dig2=$2 dig3=`bitwise_and $3 $7` dig4=0 ;;
	255.255.128.0) bits=17 dig1=$1 dig2=$2 dig3=`bitwise_and $3 $7` dig4=0 ;;
	255.255.0.0)   bits=16 dig1=$1 dig2=$2 dig3=`bitwise_and $3 $7` dig4=0 ;;

	255.254.0.0) bits=15 dig1=$1 dig2=`bitwise_and $2 $6` dig3=0 dig4=0 ;;
	255.252.0.0) bits=14 dig1=$1 dig2=`bitwise_and $2 $6` dig3=0 dig4=0 ;;
	255.248.0.0) bits=13 dig1=$1 dig2=`bitwise_and $2 $6` dig3=0 dig4=0 ;;
	255.240.0.0) bits=12 dig1=$1 dig2=`bitwise_and $2 $6` dig3=0 dig4=0 ;;
	255.224.0.0) bits=11 dig1=$1 dig2=`bitwise_and $2 $6` dig3=0 dig4=0 ;;
	255.192.0.0) bits=10 dig1=$1 dig2=`bitwise_and $2 $6` dig3=0 dig4=0 ;;
	255.128.0.0) bits=9  dig1=$1 dig2=`bitwise_and $2 $6` dig3=0 dig4=0 ;;
	255.0.0.0)   bits=8  dig1=$1 dig2=`bitwise_and $2 $6` dig3=0 dig4=0 ;;

	254.0.0.0) bits=7 dig1=`bitwise_and $1 $5` dig2=0 dig3=0 dig4=0 ;;
	252.0.0.0) bits=6 dig1=`bitwise_and $1 $5` dig2=0 dig3=0 dig4=0 ;;
	248.0.0.0) bits=5 dig1=`bitwise_and $1 $5` dig2=0 dig3=0 dig4=0 ;;
	240.0.0.0) bits=4 dig1=`bitwise_and $1 $5` dig2=0 dig3=0 dig4=0 ;;
	224.0.0.0) bits=3 dig1=`bitwise_and $1 $5` dig2=0 dig3=0 dig4=0 ;;
	192.0.0.0) bits=2 dig1=`bitwise_and $1 $5` dig2=0 dig3=0 dig4=0 ;;
	128.0.0.0) bits=1 dig1=`bitwise_and $1 $5` dig2=0 dig3=0 dig4=0 ;;
	0.0.0.0)   bits=0 dig1=0 dig2=0 dig3=0 dig4=0 ;;

	*)   bits=
	    dig1=`bitwise_and $1 $5`
	    dig2=`bitwise_and $2 $6`
	    dig3=`bitwise_and $3 $7`
	    dig4=`bitwise_and $4 $8`
	    ;;
    esac

    if [ "X$bits" = "X" ]
    then
	echo "${dig1}.${dig2}.${dig3}.${dig4}"
    else
	echo "${dig1}.${dig2}.${dig3}.${dig4}/${bits}"
    fi
}

