#!/usr/bin/python
# Licensed to the Apache Software Foundation (ASF) under one
# or more contributor license agreements.  See the NOTICE file
# distributed with this work for additional information
# regarding copyright ownership.  The ASF licenses this file
# to you under the Apache License, Version 2.0 (the
# "License"); you may not use this file except in compliance
# with the License.  You may obtain a copy of the License at
# 
#   http://www.apache.org/licenses/LICENSE-2.0
# 
# Unless required by applicable law or agreed to in writing,
# software distributed under the License is distributed on an
# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
# KIND, either express or implied.  See the License for the
# specific language governing permissions and limitations
# under the License.

import sys, os
from subprocess import PIPE, Popen
import logging
import traceback
from os.path import exists, join
from signal import alarm, signal, SIGALRM, SIGKILL

class CloudRuntimeException(Exception):
    def __init__(self, errMsg):
        self.errMsg = errMsg
    def __str__(self):
        return self.errMsg
def formatExceptionInfo(maxTBlevel=5):
    cla, exc, trbk = sys.exc_info()
    excTb = traceback.format_tb(trbk, maxTBlevel)
    msg = str(exc) + "\n"
    for tb in excTb:
        msg += tb
    return msg

class bash:
    def __init__(self, args, timeout=600):
        self.args = args
        logging.debug("execute:%s"%args)
        self.timeout = timeout
        self.process = None
        self.success = False
        self.run()

    def run(self):
        class Alarm(Exception):
            pass
        def alarm_handler(signum, frame):
            raise Alarm

        try:
            self.process = Popen(self.args, shell=True, stdout=PIPE, stderr=PIPE)
            if self.timeout != -1:
                signal(SIGALRM, alarm_handler)
                alarm(self.timeout)

            try:
                self.stdout, self.stderr = self.process.communicate()
                if self.timeout != -1:
                    alarm(0)
            except Alarm:
                os.kill(self.process.pid, SIGKILL)
                raise  CloudRuntimeException("Timeout during command execution")

            self.success = self.process.returncode == 0
        except:
            raise  CloudRuntimeException(formatExceptionInfo())

#        if not self.success: 
#            raise  CloudRuntimeException(self.getStderr())

    def isSuccess(self):
        return self.success
    
    def getStdout(self):
        return self.stdout.strip("\n")
    
    def getLines(self):
        return self.stdout.split("\n")

    def getStderr(self):
        return self.stderr.strip("\n")


def initLoging(logFile=None):
    try:
        if logFile is None:
            logging.basicConfig(level=logging.DEBUG) 
        else: 
            logging.basicConfig(filename=logFile, level=logging.DEBUG) 
    except:
        logging.basicConfig(level=logging.DEBUG) 

def writeProgressBar(msg, result=None):    
    if msg is not None:
        output = "%-80s"%msg
    elif result is True:
        output = "[ \033[92m%-2s\033[0m ]\n"%"OK"
    elif result is False:
        output = "[ \033[91m%-6s\033[0m ]\n"%"FAILED"
    sys.stdout.write(output)
    sys.stdout.flush()
    
def printError(msg):
    sys.stderr.write(msg)
    sys.stderr.write("\n")
    sys.stderr.flush()

def printMsg(msg):
    sys.stdout.write(msg+"\n")
    sys.stdout.flush()

def checkRpm(pkgName):
    chkPkg = bash("rpm -q %s"%pkgName)
    writeProgressBar("Checking %s"%pkgName, None)
    if not chkPkg.isSuccess():
        writeProgressBar(None, False)
        printError("%s is not found, please make sure it is installed. You may try 'yum install %s'\n"%(pkgName, pkgName))
        return False
    else:
        writeProgressBar(None, True)
        return True
      
def checkEnv():
   writeProgressBar("Checking is root")
   ret = bash("whoami")
   if ret.getStdout() != "root":
       writeProgressBar(None, False)
       printError("This script must run as root")
       return False
   else:
       writeProgressBar(None, True)
       
   pkgList = ['tftp-server', 'syslinux', 'xinetd', 'chkconfig', 'dhcp']
   for pkg in pkgList:
       if not checkRpm(pkg):
           return False
   return True

def exitIfFail(ret):
    if not ret: sys.exit(1) 
    
def bashWithResult(cmd):
    writeProgressBar("Executing '%s'"%cmd)
    ret = bash(cmd)
    if not ret.isSuccess():
        writeProgressBar(None, False)
        writeProgressBar(ret.getStderr() + '\n')
        return False
    else:
        writeProgressBar(None, True)
        return True
    
def configurePxeStuff(): 
    stuff = ['tftp', 'xinetd', 'dhcpd']
    cmds = ['chkconfig --level 345 %s on' % i for i in stuff]
    cmds.append('/etc/init.d/xinetd restart')
    
    for cmd in cmds:
        if not bashWithResult(cmd): return False
        
    chkIptable = bash('chkconfig --list iptables')
    if 'on' in chkIptable.getStdout():
        printMsg("Detected iptables is running, need to open tftp port 69")
        if not bashWithResult('iptables -I INPUT 1 -p udp --dport 69 -j ACCEPT'): return False
        if not bashWithResult('/etc/init.d/iptables save'): return False
        
    return True  
    
def getTftpRootDir(tftpRootDirList):
    tftpRoot = bash("cat /etc/xinetd.d/tftp | grep server_args")
    if not tftpRoot.isSuccess():
        printError("Cannot get tftp root directory from /etc/xinetd.d/tftp, here may be something wrong with your tftp-server, try reinstall it\n")
        return False
    tftpRootDir = tftpRoot.getStdout()
    index = tftpRootDir.find("/")
    if index == -1:
        printError("Wrong server_arg in /etc/xinetd.d/tftp (%s)"%tftpRootDir)
        return False
    tftpRootDir = tftpRootDir[index:]
    tftpRootDirList.append(tftpRootDir)
    return True

def preparePING(tftpRootDir):
    pingFiles = ['boot.msg', 'initrd.gz', 'kernel', 'pxelinux.0']
    pingDir = "/usr/share/PING"
    
    for f in pingFiles:
        path = join(pingDir, f)
        if not exists(path):
            printError("Cannot find %s, please make sure PING-3.01 is installed"%path)
            return False
        if not bashWithResult("cp -f %s %s"%(path, tftpRootDir)): return False
     
    if not bashWithResult("mkdir -p %s/pxelinux.cfg"%tftpRootDir): return False
    
    return True

def prepareSyslinux(tftpRootDir):
    pkg = '/usr/share/syslinux/pxelinux.0'
    if not os.path.exists(pkg):
        printError('cannot find pxelinux.0 on system. is syslinux installed?')
        return False

    cp = "cp -f %s %s" % (pkg, tftpRootDir)
    if not bashWithResult(cp):
        return False

    return True

            
        
if __name__ == "__main__":
    initLoging("/tmp/cloud-setup-baremetal.log")
    tftpRootDirList = []
    
    exitIfFail(checkEnv())
    exitIfFail(configurePxeStuff())
    exitIfFail(getTftpRootDir(tftpRootDirList))
    
    tftpRootDir = tftpRootDirList[0].strip()
    #exitIfFail(preparePING(tftpRootDir))
    exitIfFail(prepareSyslinux(tftpRootDir))
    printMsg("")
    printMsg("Setup BareMetal PXE server successfully")
    printMsg("TFTP root directory is: %s\n"%tftpRootDir)
    sys.exit(0)
    
