#!/usr/bin/env bash
#set -x

WHICH=/usr/bin/which
WGET=$($WHICH wget)
GREP=$($WHICH grep)
AWK=$($WHICH awk)
SED=$($WHICH sed)
WC=$($WHICH wc)
RM=$($WHICH rm)
MV=$($WHICH mv)
TEMPORARY_FILE="${HOME}/get-oui-$(echo $RANDOM).tmp"
DEFAULT_FETCH_URL="http://standards.ieee.org/regauth/oui/oui.txt"
DEFAULT_OUTPUT_FILE="ieee-oui.txt"
VERBOSE=FALSE

#########
# USAGE #
#########
usage()
{
	echo "Usage: get-oui [options]"
	echo "Fetch the Ethernet OUI file from the IEEE website, and save it in the format"
	echo "used by arp-scan."
	echo ""
	echo "'options' is one or more of:"
	echo "        -h Display this usage message."
	echo "        -f FILE Specify the output OUI file. Default=ieee-oui.txt"
	echo "        -u URL Specify the URL to fetch the OUI data from."
	echo "           Default=http://standards.ieee.org/regauth/oui/oui.txt"
	echo "        -v Give verbose progress messages."
	echo ""
}

#######################
# OUI File generation #
#######################
generateoui()
{
	echo "# ieee-oui.txt -- Ethernet vendor OUI file for arp-scan"  > "${DEFAULT_OUTPUT_FILE}"
	echo "#" >> "${DEFAULT_OUTPUT_FILE}"
	echo "# This file contains the Ethernet vendor OUIs for arp-scan.  These are used" >> "${DEFAULT_OUTPUT_FILE}"
	echo "# to determine the vendor for a give Ethernet interface given the MAC address." >> "${DEFAULT_OUTPUT_FILE}"
	echo "#" >> "${DEFAULT_OUTPUT_FILE}"
	echo "# Each line of this file contains an OUI-vendor mapping in the form:" >> "${DEFAULT_OUTPUT_FILE}"
	echo "#" >> "${DEFAULT_OUTPUT_FILE}"
	echo "# <OUI><TAB><Vendor>" >> "${DEFAULT_OUTPUT_FILE}"
	echo "#" >> "${DEFAULT_OUTPUT_FILE}"
	echo "# Where <OUI> is the first three bytes of the MAC address in hex, and <Vendor>" >> "${DEFAULT_OUTPUT_FILE}"
	echo "# is the name of the vendor." >> "${DEFAULT_OUTPUT_FILE}"
	echo "#" >> "${DEFAULT_OUTPUT_FILE}"
	echo "# Blank lines and lines beginning with \"#\" are ignored." >> "${DEFAULT_OUTPUT_FILE}"
	echo "#" >> "${DEFAULT_OUTPUT_FILE}"
	echo "# This file was automatically generated by get-oui at $(date "+%Y-%m-%d %H:%M:%S")" >> "${DEFAULT_OUTPUT_FILE}"
	echo "# using data from http://standards.ieee.org/regauth/oui/oui.txt" >> "${DEFAULT_OUTPUT_FILE}"
	echo "#" >> "${DEFAULT_OUTPUT_FILE}"
	echo "# Do not edit this file.  If you want to add additional MAC-Vendor mappings," >> "${DEFAULT_OUTPUT_FILE}"
	echo "# edit the file mac-vendor.txt instead." >> "${DEFAULT_OUTPUT_FILE}"
	echo "#" >> "${DEFAULT_OUTPUT_FILE}"
	$GREP "(base 16)" "${TEMPORARY_FILE}" | $SED 's|(base 16)|\t|g' | $AWK '{$1=$1;print}' | $AWK '{print $1"\t" substr($0, index($0,$2)) }' >> "${DEFAULT_OUTPUT_FILE}"
	$RM "${TEMPORARY_FILE}"
}

while getopts hvf:u: name
do
	case $name in
		h)
			hflag=1
			usage
			exit 2
			;;
		v)
			vflag=1
			VERBOSE=TRUE
			;;
		f)
			fflag=1
			DEFAULT_OUTPUT_FILE="$OPTARG"
			;;
		u)
			uflag=1
			DEFAULT_FETCH_URL="$OPTARG"
			;;
		*)
			usage
			exit 2
			;;
	esac
done

if [ $VERBOSE == "TRUE" ] ; then
	if [[ -f "${DEFAULT_OUTPUT_FILE}" ]] ; then
		echo "Renaming ${DEFAULT_OUTPUT_FILE} to ${DEFAULT_OUTPUT_FILE}.bak"
		$MV "${DEFAULT_OUTPUT_FILE}" "${DEFAULT_OUTPUT_FILE}.bak"
	fi
	echo "Fetching OUI data from ${DEFAULT_FETCH_URL}"
	FETCHED=$(LANG=C $WGET -O "${TEMPORARY_FILE}" "${DEFAULT_FETCH_URL}" 2>&1 | $GREP Length | $AWK '{print $2}' | $SED 's|,||g')
	echo "Fetched ${FETCHED} bytes"
	echo "Opening output file ${DEFAULT_OUTPUT_FILE}"
	generateoui
	echo "$($GREP -v ^# ${DEFAULT_OUTPUT_FILE} | $WC -l) OUI entries written to file ${DEFAULT_OUTPUT_FILE}"
else
	if [[ -f "${DEFAULT_OUTPUT_FILE}" ]] ; then
		$MV "${DEFAULT_OUTPUT_FILE}" "${DEFAULT_OUTPUT_FILE}.bak"
	fi
	$WGET -O "${TEMPORARY_FILE}" "${DEFAULT_FETCH_URL}" 2>&1 | $GREP Length | $AWK '{print $2}' | $SED 's|,||g'
	generateoui
fi
