xcat-core/xCAT-genesis-scripts/bin/dodiscovery

244 lines
10 KiB
Plaintext
Raw Normal View History

#!/bin/bash
minixcatd.awk &
PUBKEY=`openssl rsa -in /etc/xcat/privkey.pem -pubout 2> /dev/null|grep -v "PUBLIC KEY"`
PUBKEY=`echo $PUBKEY|sed -e 's/ //g'`
export PUBKEY
echo "Beginning node discovery process"
for nic in `ip link|grep mtu|grep -v LOOPBACK|grep -v usb|grep -v ,LOWER_UP|awk -F: '{print $2}'`; do
ip link set $nic up
done
waitforlink=100
while [ ! -z "$NICSTOBRINGUP" -a $waitforlink -gt 0 ]; do
NICSTOBRINGUP=`ip link|grep mtu|grep -v LOOPBACK|grep -v usb|grep -v ,LOWER_UP|awk -F: '{print $2}'`
waitforlink=$((waitforlink - 1))
sleep 0.1
if [ $waitforlink = 1 ]; then
echo "No link detected on $NICSTOBRINGUP"
fi
done
NICSGETTINGADDR=`ip link|grep mtu|grep -v LOOPBACK|grep -v usb|grep ,LOWER_UP|awk -F: '{print $2}'`
timewaiting=0
echo "Waiting for nics to get addresses"
while [ ! -z "$NICSGETTINGADDR" -a $timewaiting != 700 ]; do
NEWNICSGETTINGADDR=""
for nic in $NICSGETTINGADDR; do
if ! ip addr show dev $nic |grep -v inet6|grep inet >/dev/null; then
NEWNICSGETTINGADDR="$NEWNICSGETTINGADDR $nic"
else
echo -n "$nic|"
ip addr show dev $nic |grep -v inet6|grep inet|sed -e s/\\/.*//|awk '{print $2}'
fi
done
sleep 0.1
timewaiting=$((timewaiting+1))
if [ $timewaiting = 699 ]; then
echo "No DHCP answer for $nic, ignoring interface"
fi
NICSGETTINGADDR=$NEWNICSGETTINGADDR
done
if [ $timewaiting != 700 -a $timewaiting -gt 450 ]; then
echo "Got an address, but it took inordinately long, you may want to check spanning tree configuration"
fi
echo "Network configuration complete, commencing transmit of discovery packets"
XCATPORT=3001
export XCATPORT
for parm in `cat /proc/cmdline`; do
key=`echo $parm|awk -F= '{print $1}'`
if [ "$key" = "xcatd" ]; then
XCATMASTER=`echo $parm|awk -F= '{print $2}'|awk -F: '{print $1}'`
XCATPORT=`echo $parm|awk -F= '{print $2}'|awk -F: '{print $2}'`
fi
done
#time to make our packet...
while [ ! -r /restart ]; do
MTM=unknown
SERIAL=unknown
ARCH=unknown
ARCH=`uname -m` #32-bit only is old news
PLATFORM=unknown
if [ -r /sys/devices/virtual/dmi/id/product_name ]; then #x86
PRODNAME=`cat /sys/devices/virtual/dmi/id/product_name`
IAMAVM=0
if [ "$PRODNAME" = "KVM" ]; then
IAMAVM=1
MTM=KVM
elif [ "$PRODNAME" = "VMware Virtual Platform" ]; then
IAMAVM=1
MTM=VMware
else
MTM=`cat /sys/devices/virtual/dmi/id/product_name|awk -F'[' '{print $2}'|awk -F']' '{print $1}'`
SERIAL=`cat /sys/devices/virtual/dmi/id/product_serial`
fi
CPUCOUNT=`cat /proc/cpuinfo |grep "model name"|wc -l`
grep "model name" /proc/cpuinfo | while read line; do #to avoid pulling in tail, we do a goofy thing
echo $line > /tmp/cpumod
done
CPUTYPE=`cat /tmp/cpumod|awk -F':' '{print $2}'|sed -e 's/^ //'`
UUID=`sed -e 's/\(..\)\(..\)\(..\)\(..\)-\(..\)\(..\)-\(..\)\(..\)/\4\3\2\1-\6\5-\8\7/' /sys/devices/virtual/dmi/id/product_uuid`
elif [ -r /proc/device-tree/model ]; then #POWER
#MTM=`cat /proc/device-tree/model |awk -F, '{print $2}'`
MTM=`cat /proc/device-tree/model | sed -e 's/\^.*,//'`
CPUCOUNT=`cat /proc/cpuinfo |grep -e "^cpu\s*:"|wc -l`
PLATFORM=`cat /proc/cpuinfo | grep -e "^platform\s*:" | awk '{print \$3}'`
grep -e "^cpu\s*:" /proc/cpuinfo | while read line; do #to avoid pulling in tail, we do a goofy thing
echo $line > /tmp/cpumod
done
CPUTYPE=`cat /tmp/cpumod|awk -F':' '{print $2}'|sed -e 's/^ //'`
SERIAL=`cat /proc/device-tree/system-id`
UUID=`sed -e 's/\(..\)\(..\)\(..\)\(..\)-\(..\)\(..\)-\(..\)\(..\)/\4\3\2\1-\6\5-\8\7/' /proc/sys/kernel/random/uuid`
fi
#CPUCOUNT=`cat /proc/cpuinfo |grep "model name"|wc -l`
# The MEMORY will look like this: 32868920
MEMORY=`cat /proc/meminfo |grep MemTotal|awk '{printf "%.0fMB\n", $2/1024}'`
# The MEMORY will look like this: 32GiB
#MEMORY=`lshw -C memory -short |grep "System Memory"|awk -F' ' '{print $3}'`
# The DISKSIZE will look like this: /dev/sda:250GB,/dev/sdb:250GB
#DISKSIZE=`lshw -C disk -short |grep disk |awk -F' ' '{print $2":"$4}'|sed 'N;s/\n/,/'`
# The DISKSIZE will look like this: sdb:250GB,sda:250GB
DISKSIZE=`cat /proc/partitions |grep -e "sd.\>" |awk -F' ' '{printf "%s:%.0fGB\n", $4, $3*0.000001024}' |sed 'N;s/\n/,/'`
#UUID=`sed -e 's/\(..\)\(..\)\(..\)\(..\)-\(..\)\(..\)-\(..\)\(..\)/\4\3\2\1-\6\5-\8\7/' /sys/devices/virtual/dmi/id/product_uuid`
#grep "model name" /proc/cpuinfo | while read line; do #to avoid pulling in tail, we do a goofy thing
# echo $line > /tmp/cpumod
#done
#CPUTYPE=`cat /tmp/cpumod|awk -F':' '{print $2}'|sed -e 's/^ //'`
echo '<xcatrequest>' > /tmp/discopacket
echo "<command>findme</command>" >> /tmp/discopacket
echo "<arch>$ARCH</arch>" >> /tmp/discopacket
if [ "$IAMAVM" = 1 ]; then
echo "<nodetype>virtual</nodetype>" >> /tmp/discopacket
fi
echo "<cpucount>$CPUCOUNT</cpucount>" >> /tmp/discopacket
echo "<cputype>$CPUTYPE</cputype>" >> /tmp/discopacket
echo "<memory>$MEMORY</memory>" >> /tmp/discopacket
echo "<disksize>$DISKSIZE</disksize>" >> /tmp/discopacket
if [ "$UUID" != "unknown" ]; then
echo "<uuid>$UUID</uuid>" >> /tmp/discopacket
fi
if [ "$MTM" != "unknown" ]; then
echo "<mtm>$MTM</mtm>" >> /tmp/discopacket
fi
if [ "$SERIAL" != "unknown" ]; then
echo "<serial>$SERIAL</serial>" >> /tmp/discopacket
fi
if [ "$PLATFORM" != "unknown" ]; then
echo "<platform>$PLATFORM</platform>" >> /tmp/discopacket
fi
#so we have some cases where DMI table explictly records every function number, and some where only first function is enumerated
#so for each onboard device, we record it. If it is also the first function, we'll seek out other function numbers and append
#if that other function number does not show up in its own dmi type 41 record
for onboard in `dmidecode -t 41|egrep '(Type:|Bus Address)'|grep -A1 Ethernet|grep -v Ethernet|sed -e 's/.*Address: //'`; do
obdevs=("${obdevs[@]}" $onboard)
if [ ${onboard#*.}=0 ]; then
truncslot=${onboard%.*}
for obslot in `grep $truncslot /sys/class/net/*/device/uevent|sed -e s/.*=//`; do
if ! dmidecode -t 41|grep $obslot > /dev/null; then
obdevs=("${obdevs[@]}" $obslot)
fi
done
fi
done
#TODO: downed nics, also examine /sys/bus/pci/*/ for more network class devices that might not have driver suppert
for dev in `ip link|grep -B1 ether|grep UP|awk '{print $2}'|sed -e s/://|grep -v usb0`; do
FIRMDESC=""
ONBOARDINDEX=""
DRIVER=`grep DRIVER /sys/class/net/$dev/device/uevent|awk -F= '{print $2}'`
PCI_SLOT=`grep PCI_SLOT_NAME /sys/class/net/$dev/device/uevent|awk -F= '{print $2}'`
ADDRESS=`ip address show dev $dev|grep "inet "|grep global|awk '{print $2}'`
MAC=`ip link show dev $dev|grep ether|awk '{print $2}'| tr /a-f/ /A-F/`
if [ ! -z "$PCI_SLOT" ]; then
SLOTNAME=`dmidecode -t 9|egrep '(Designation|Address)'|grep -B1 $PCI_SLOT|grep Designation|sed -e 's/.*Designation:[ ]*//'`
if [ -z "$SLOTNAME" ]; then #check for on board device
index=1
for s in ${obdevs[@]}; do
if [ "$s" = "$PCI_SLOT" ]; then
ONBOARDINDEX=$index
break
fi
index=$((index+1))
done
if [ ! -z "$ONBOARDINDEX" ]; then
FIRMDESC=`dmidecode -t 41|egrep '(Designation|Address)' |grep -B 1 $PCI_SLOT|grep Designation|sed -e 's/.*: //'`
if [ -z "$FIRMDESC" ]; then
SHORTPCISLOT=${PCI_SLOT%.*}
FIRMDESC=`dmidecode -t 41|egrep '(Designation|Address)' |grep -B 1 $SHORTPCISLOT|grep Designation|sed -e 's/.*: //'`
fi
SLOTNAME="Onboard Ethernet $ONBOARDINDEX"
fi
fi
fi
echo "<mac>$DRIVER|$dev|$MAC|$ADDRESS</mac>" >> /tmp/discopacket
echo "<nic>" >> /tmp/discopacket
echo " <devname>$dev</devname>" >> /tmp/discopacket
echo " <driver>$DRIVER</driver>" >> /tmp/discopacket
if [ ! -z "$ADDRESS" ]; then
echo " <ip4address>$ADDRESS</ip4address>" >> /tmp/discopacket
fi
echo " <hwaddr>$MAC</hwaddr>" >> /tmp/discopacket
if [ ! -z "$PCI_SLOT" ]; then
echo " <pcidev>$PCI_SLOT</pcidev>" >> /tmp/discopacket
fi
if [ ! -z "$SLOTNAME" ]; then
echo " <location>$SLOTNAME</location>" >> /tmp/discopacket
fi
if [ ! -z "$ONBOARDINDEX" ]; then
echo " <onboardeth>$ONBOARDINDEX</onboardeth>" >> /tmp/discopacket
fi
if [ ! -z "$FIRMDESC" ]; then
echo " <firmdesc>$FIRMDESC</firmdesc>" >> /tmp/discopacket
fi
myswitch=`lldptool -n -i $dev -t -V sysName|grep -v 'System Name TLV'|sed -e 's/^ *//'`
if [ ! -z "$myswitch" -a "$myswitch" != "Agent instance for device not found" ]; then
echo " <switchname>$myswitch</switchname>" >> /tmp/discopacket
fi
for switchaddr in `lldptool -i $dev -n -t -V mngAddr|grep IP|sed -e 's/.*:.//'`; do
if [ "$switchaddr" = "Agent instance for device not found" ]; then break; fi
echo " <switchaddr>$switchaddr</switchaddr>" >> /tmp/discopacket
done
myswitchdesc=`lldptool -n -i $dev -t -V sysDesc|grep -v 'System Description TLV'|sed -e 's/^ *//'`
if [ ! -z "$myswitchdesc" -a "$myswitchdesc" != "Agent instance for device not found" ]; then
echo " <switchdesc>$myswitchdesc</switchdesc>" >> /tmp/discopacket
fi
myport=`lldptool -n -i $dev -t -V portDesc|grep -v 'Port Description TLV'|sed -e 's/^ *//'`
if [ ! -z "$myport" -a "$myswitchdesc" != "Agent instance for device not found" ]; then
echo " <switchport>$myport</switchport>" >> /tmp/discopacket
fi
echo "</nic>" >> /tmp/discopacket
done
echo "<xcatpubkey>$PUBKEY</xcatpubkey>" >> /tmp/discopacket #this is not secure to use by itself, switch sourced pubkey for security
echo "<sha512sig>" >> /tmp/discopacket
echo "</sha512sig>" >> /tmp/discopacket
echo "</xcatrequest>" >> /tmp/discopacket
openssl dgst -sha512 -out /tmp/discopacket.sha512 -sign /etc/xcat/privkey.pem /tmp/discopacket
openssl enc -e -a -in /tmp/discopacket.sha512 > /tmp/discopacket.b64sig
cat /tmp/discopacket |while read line; do
if [ "$line" = "</sha512sig>" ]; then
cat /tmp/discopacket.b64sig >> /tmp/discopacket.new
fi
echo $line >> /tmp/discopacket.new
done
mv /tmp/discopacket.new /tmp/discopacket
rm -f /tmp/discopacket.gz
gzip -9 /tmp/discopacket
if [ ! -z "$XCATMASTER" ]; then
(cat /tmp/discopacket.gz | udpcat.awk $XCATMASTER $XCATPORT ) &
fi
for dhcps in `grep dhcp-server /var/lib/dhclient/dhclient.leases|awk '{print $4}'|sed -s 's/;//'`; do
(cat /tmp/discopacket.gz | udpcat.awk $dhcps $XCATPORT ) &
done
#cat /tmp/discopacket
sleep 5
done
/bin/restart