# -*- coding: UTF-8 -*-

import re
import string
import resourceParse 
import os
import filePathParse
import hashlib
import tarfile
import shutil
import common

# 使用TLV命令安装热补丁 20131130 added Begin
import time
from com.huawei.ism.tlv.bean import Param
from com.huawei.ism.tlv.docoder import ParamType
from com.huawei.ism.tlv.bean import Record
from com.huawei.ism.tlv.lang import UnsignedInt32
from com.huawei.ism.tlv import TLVUtils
from com.huawei.ism.tool.protocol.tlv.cmds import CommandConstans
from com.huawei.ism.tool.protocol.sftp import SftpProgressInterface
from com.huawei.ism.tool.protocol.tlv.cmds.CommandConstans import UpgradeStatus
from java.io import File
from cbb.frame.util.tar_util import UnZipLimit, get_safe_entry_name

# 命令执行超时时间
CMD_DEFAULT_TIMEOUT = 60

#升级相关命令
OM_MSG_OP_UPGRADE_NOTIFY = 8599117950
OM_MSG_OP_UPGRADE_QUERY_STATUS = 8599109759
OM_MSG_OP_UPGRADE_GET_ACTIVE_TYPE = 8599109757

#执行状态枚举值
UPGRADE_STEP_STATUS_EXECUTING       =1
UPGRADE_STEP_STATUS_SUCCEED         =2
UPGRADE_STEP_STATUS_FAILED          =3

#升级相关错误码
RETURN_UPGRADE_NORMAL = 0                      #状态正常
RETURN_DISSATISFY_USBCONDITION = 1             #不满足USB条件
RETURN_SYSTEM_ABNORMAL = 2                     #系统状态不为Normal
RETURN_UPGRADE_SINGLE_CONTROLLER = 3           #当前为单控
RETURN_UPGRADE_SINGLE_CONNECTION = 4           #当前为单链路
RETURN_UPGRADE_LUN_FORMATING = 5               #Lun格式化中
RETURN_UPGRADE_VERSION_NOT_SUPPORT_ONLINE = 6  #版本兼容性信息不允许在线升级
RETURN_UPGRADE_UPGRADING = 7                   #当前系统正在升级中
RETURN_UPGRADE_FW_ACTURAL_VERSION_NOT_SAME = 8 #存在固件版本与系统配置不一致
RETURN_UPGRADE_CHECK_ITEM_WARNING = 9          #警告
RETURN_UPGRADE_CHECK_ITEM_FAIL = 10            #失败
RETURN_UPGRADE_FORBID_ALTERNATION_VERSION = 11 #黑名单禁止升级
RETURN_UPGRADE_HOT_PATCH_PACKAGE_ERR = 12           #热补丁包错误
RETURN_UPGRADE_HOT_PATCH_COMPATIBLE_ERR = 13        #热补丁包与系统软件不匹配
RETURN_UPGRADE_HOT_PATCH_EXIST = 14                 #当前需要安装的热补丁已经存在
RETURN_UPGRADE_HOT_PATCH_MEMORY_NOT_ENOUGH = 15     #热补丁已超过最大规格
RETURN_UPGRADE_HOT_PATCH_NOT_EXIST = 16             #系统不存在热补丁
RETURN_UPGRADE_HOT_PATCH_SYS_BUSY = 17              #系统忙无法安装热补丁
RETURN_UPGRADE_HOT_PATCH_STATUS_ERR = 18            #当前运行热补丁状态错误
RETURN_UPGRADE_HOT_PATCH_ROLLBACK_ERR = 19          #当前没有可回退的热补丁包
RETURN_UPGRADE_ABNORAMAL_REASON_BUTT = 20
# 使用TLV命令安装热补丁 20131130 added End

# 补丁工具代码流程优化 modified 20131112 Begin
#检查结果
CHECK_RESULT_PASS       =0
CHECK_RESULT_NOTPASS    =1
CHECK_RESULT_WARNING    =2
# 补丁工具代码流程优化 modified 20131112 End

VERSIONS_MAPFILE = r"..{0}conf{0}versionsConf".format(os.sep)
TLV_EXECUTE_SHELL_COMMOND = 0x200640058

# 使用TLV命令安装热补丁 20131130 added Begin
# *************************************************************#
# 函数名称: uploadHotPatchPackage
# 功能说明: 上传热补丁升级包
# 其 他   :  无
# *************************************************************#  
def uploadHotPatchPackage(dataDict, fileName):

    dev = dataDict["dev"]
    sftp = dataDict['sftp']
    tlvCon = dataDict["tlv"]
    logger = dataDict.get("logger")
    resource = dataDict["resource"]
    
    #获取热补丁包上传路径
    pkgTypeParam0 = Param(0, ParamType.UNSIGN_INT, UnsignedInt32(3))
    pkgTypeParam1 = Param(1, ParamType.STRING, "")
    params = TLVUtils.paramList(pkgTypeParam0, pkgTypeParam1)

    #获取热补丁升级包上传路径
    retRec = tlvCon.invoke(CommandConstans.OM_MSG_OP_GET_PACKAGE_DIR, params, CMD_DEFAULT_TIMEOUT)
    
    uploadPath = retRec.getParamStrValue(1)
    
    logger.info("pkg upload path = " + str(uploadPath))
    
    #上传升级包
    try:
        sftp.putFile(dev.getIp(), fileName, uploadPath, dev.getLoginUser(), None)
    except:
        return (False, resource.get('2021'))
    
    #通知其他控制器同步升级包
    logger.info('notify upgradepackage path')
    devPkgPath = ":" + uploadPath
    pkgPathParam = Param(0, ParamType.STRING, devPkgPath)
    params = TLVUtils.paramList(pkgPathParam)
    
    retRec = tlvCon.invoke(CommandConstans.OM_MSG_OP_NOTIFY_PACKAGE_PATH, params, CMD_DEFAULT_TIMEOUT)
    
    #处理正常返回
    return (True, "")

# *************************************************************#
# 函数名称: checkActiveMode
# 功能说明: 获取热补丁激活方式
# 其 他   :  无
# *************************************************************#  
def checkActiveMode(dataDict):

    tlvCon = dataDict["tlv"]
    logger = dataDict.get("logger")
    resource = dataDict["resource"]
    
    #获取热补丁包激活类型
    msgParam0 = Param(0, ParamType.UNSIGN_INT, UnsignedInt32(3))
    msgParam1 = Param(1, ParamType.UNSIGN_INT, UnsignedInt32(0))
    params = TLVUtils.paramList(msgParam0, msgParam1)
    
    rec = tlvCon.invoke(OM_MSG_OP_UPGRADE_GET_ACTIVE_TYPE, params, CMD_DEFAULT_TIMEOUT)
    
    #校验热补丁激活类型  
    modelCode = rec.getParamIntValue(2).intValue()
    failReason = rec.getParamIntValue(3).intValue()
    logger.info("device return upgrade model is :" + str(modelCode))
    logger.info("device return upgrade model check fail reason code is:" + str(failReason))
    
    #热补丁只能在线
    if modelCode == 1:
        return (True, "")
    else:
        #获取错误码信息
        errMsg = resource.get('2024')
        if resource.has_key('errCode_' + str(failReason)):
            errMsg += " " + resource.get('errCode_' + str(failReason))
        else:
            errMsg += " " + str(failReason)

        return (False, errMsg)

# *************************************************************#
# 函数名称: installHotPatchPackage
# 功能说明: 安装热补丁升级包
# 其 他   :  无
# *************************************************************#  
def installHotPatchPackage(dataDict):

    tlvCon = dataDict["tlv"]
    logger = dataDict.get("logger")
    resource = dataDict["resource"]

    #构造热补丁升级命令
    msgParam0 = Param(0, ParamType.UNSIGN_INT, UnsignedInt32(3))    
    msgParam1 = Param(1, ParamType.UNSIGN_INT, UnsignedInt32(2))
    msgParam2 = Param(2, ParamType.UNSIGN_INT, UnsignedInt32(1))
    params = TLVUtils.paramList(msgParam0, msgParam1, msgParam2)

    logger.info('start to notify to install the hotpatch')
    #下发升级命令
    tlvCon.invoke(OM_MSG_OP_UPGRADE_NOTIFY, params, CMD_DEFAULT_TIMEOUT)

    #查询升级状态
    logger.info('start to check upgrade processing status')
    status = UPGRADE_STEP_STATUS_EXECUTING
    checkCounter = 0

    #构造查询升级状态参数
    msgParam0 = Param(0, ParamType.UNSIGN_INT, UnsignedInt32(2))
    msgParam1 = Param(1, ParamType.UNSIGN_INT, UnsignedInt32(2))
    params = TLVUtils.paramList(msgParam0, msgParam1)
    
    #循环查询升级热补丁状态
    while UPGRADE_STEP_STATUS_EXECUTING == status:

        #每隔5秒查询一次，最多检查10分钟
        time.sleep(5)
        logger.info("Sleep 5s, check hotpatch install process counter:" + str(checkCounter))
        if checkCounter < 120:
            checkCounter += 1
        else:
            logger.error("Sleep counter for 10 minutes, check hotpatch install process failed.")
            return (False, resource.get('2027')) 
        
        #下发查询升级执行状态命令
        rec = tlvCon.invoke(OM_MSG_OP_UPGRADE_QUERY_STATUS, TLVUtils.paramList(), CMD_DEFAULT_TIMEOUT)
        
        logger.info("Query the upgrade status:" + str(rec))
        
        #判断升级状态
        status = rec.getParamIntValue(2).intValue()
        if UPGRADE_STEP_STATUS_FAILED == status:
            return (False, resource.get('2028'))
        elif UPGRADE_STEP_STATUS_SUCCEED == status:
            return (True, '')

# 使用TLV命令安装热补丁 20131130 added End

# *************************************************************#
# 函数名称: getFileSHA256CheckCode
# 功能说明: 获取文件的SHA256校验码
# 其 他   :  无
# *************************************************************#  
def getFileSHA256CheckCode(fileName):
    
    hash_value = ''
    
    #使用SHA256加密
    hash_new = hashlib.sha256()
    #试图以二进制格式打开文件
    try:
        #将二进制文件流加密
        hash_value = getHashHex(fileName, hash_new)
    except IOError:
        pass

    return hash_value


def getHashHex(fileName, hash_new):
    with open(fileName, 'rb') as fp:
        # 读取文件块,直到读完文件
        while True:
            data = fp.read()
            if not data:
                break
            hash_new.update(data)
    return hash_new.hexdigest()

# *************************************************************#
# 函数名称: specialProcessBeforeInstall
# 功能说明: 安装热补丁前的特殊操作
# 其 他   :  无
# *************************************************************#
def specialProcessBeforeInstall(beforeCheckDict):

    upgradeErrMsg = ""

    #获取变量信息
    ssh = beforeCheckDict["ssh"]
    resource = beforeCheckDict["resource"]
    logger = beforeCheckDict["logger"]
    curHotPatchVer = beforeCheckDict["curHotPatchVer"]
    installHotPatchVer = beforeCheckDict["installHotPatchVer"]

    logger.info("[Specail process] Current system hotpatch version:" + str(curHotPatchVer))
    logger.info("[Specail process] Installed hotpatch package version:" + str(installHotPatchVer))

    #热补丁版本号判断
    if curHotPatchVer == "":
        return (True, "")
    if curHotPatchVer.find("SPH") == -1 or installHotPatchVer.find("SPH") == -1:
        upgradeErrMsg = resource.get('2003')
        return (False, upgradeErrMsg)
    
    #获取补丁规范版本号：SPHh01
    curIndex = curHotPatchVer.index("SPH")
    upgIndex = installHotPatchVer.index("SPH")
    curSphVer = curHotPatchVer[curIndex:curIndex+6]
    upgSphVer = installHotPatchVer[upgIndex:upgIndex+6]
    
    curSpcVer = beforeCheckDict["curSpcVerBefore"]
    verSpcList = ["V100R005C00SPC700", "V100R005C01SPC700","V100R005C00SPC900", "V100R005C01SPC900"]
    logger.info("The curSpcVer is:" + unicode(curSpcVer))
    #补丁为空即没有安装补丁的情况在第222行已经返回了，运行到此：版本为对应版本且安装热补丁
    #之前补丁检查已经对版本前后关系进行了过滤，确定补丁版本是要安装补丁之前的版本
    #SPC900热补丁要采用删除补丁的方式
    try:
        if curSpcVer in verSpcList:
            flag = common.changeCli2Developer(beforeCheckDict)
            if not flag:
                upgradeErrMsg = resource.get("2030")
                #报错提示：整体报卸载热补丁失败
                return (False, upgradeErrMsg)
            
            retryTimes = 2 #重试两次
            for i in range(retryTimes):
                cliRet = ssh.execCmd("delhotpatch")
                if re.search("Are you sure", cliRet, re.IGNORECASE):
                    cliRet1 = ssh.execCmd("y")
                    if re.search("Succeeded", cliRet1, re.IGNORECASE):
                        #卸载成功之后要睡眠一分钟
                        time.sleep(60)
                        common.changeAnyModel2Cli(ssh)
                        return (True, "")
                time.sleep(5)   #删除失败，休眠5秒再卸载一次
            
            #删除热补丁失败，返回错误
            common.changeAnyModel2Cli(ssh)
            upgradeErrMsg = resource.get('2031')
            return (False, upgradeErrMsg)
    except Exception:
        common.changeAnyModel2Cli(ssh)
        upgradeErrMsg = resource.get('2031')
        return (False, upgradeErrMsg)

    try:
        #当前已安装SPHh01或者SPH701热补丁，安装同一系统版本的最新的补丁需要先卸载
        #当前热补丁为SPH701，安装SPH702或以上热补丁需要卸载
        if (curSphVer in ["SPHh01"] and curSphVer[0:4] == upgSphVer[0:4]\
            and curSphVer < upgSphVer) :
            #使用Cli命令回滚热补丁
            cliRet = ssh.execCmd("rollbackhotpatch")
            if re.search("Are you sure", cliRet, re.IGNORECASE):
                cliRet1 = ssh.execCmd("y")
                if re.search("Succeeded", cliRet1, re.IGNORECASE):
                    #卸载成功之后要睡眠一分钟
                    time.sleep(60)
                    return (True, "")
            
            #卸载失败，休眠5秒再卸载一次
            time.sleep(5)
            cliRet = ssh.execCmd("rollbackhotpatch")
            if re.search("Are you sure", cliRet, re.IGNORECASE):
                cliRet1 = ssh.execCmd("y")
                if re.search("Succeeded", cliRet1, re.IGNORECASE):
                    #卸载成功之后要睡眠一分钟
                    time.sleep(60)
                    return (True, "")
            
            #回滚热补丁失败，返回错误
            upgradeErrMsg = resource.get('2029')
            return (False, upgradeErrMsg)
        else:
            return (True, "")
    except Exception :
        upgradeErrMsg = resource.get('2029')
        return (False, upgradeErrMsg)
    
    
# 补丁工具代码流程优化 modified 20131112 Begin
# *************************************************************#
# 函数名称: getCurSPCVerVerInfo
# 功能说明: 通过解析versionsconf文件获取当前系统对应的热补丁信息
# 其 他   :  无
# *************************************************************#
def getCurSPCVerVerInfo(DeviceType, curSysVer, logger):

    hotPatchDeviceTypeList = []
    hotPatchVersion = ""
    hotPatchSysSpcVersion = ""
    
    scriptPath = os.path.split(os.path.realpath(__file__))[0]
    verConfFilePath = scriptPath + os.sep + VERSIONS_MAPFILE
    
    #解析versionConf文件
    file = open(verConfFilePath)
    fileInfo = file.read()
    file.close()
    if not re.search(curSysVer, fileInfo, re.IGNORECASE):
        return ("", "")

    verMapLineList = fileInfo.splitlines()
    for line in verMapLineList:
        field = line.split("=")
        if len(field) != 4:
            continue       
        #获取热补丁支持型号列表和配套的SPC版本号
        hotPatchDeviceTypeList = field[1].strip().split(",")
        hotPatchSysSpcVersion = field[2].strip()
        #当前设备型号和系统版本满足要求
        if DeviceType in hotPatchDeviceTypeList and curSysVer == hotPatchSysSpcVersion:
            hotPatchVersion = field[0].strip()
            break

    return hotPatchVersion

# 补丁工具代码流程优化 modified 20131112 End
# *************************************************************#
# 函数名称: upgradeProcess
# 功能说明: 热补丁升级执行函数
# 其 他   :  无
# *************************************************************#
def upgradeProcess(dataDict, filePath, specialPkgFlag):

    logger = dataDict['logger']
    #通过特殊热补丁包Flag做分支处理
    if specialPkgFlag:
        logger.info("Run the special package install process!")
        iRet = upgradeProcessSpecial(dataDict, filePath)
    else:
        logger.info("Run the normal package install process!")
        iRet = upgradeProcessNormal(dataDict, filePath)
        
    return iRet

# 使用TLV命令安装热补丁 20131130 modified Begin
# *************************************************************#
# 函数名称: upgradeProcessNormal
# 功能说明: 正常热补丁升级包的升级执行函数
# 其 他   :  无
# *************************************************************#
def upgradeProcessNormal(dataDict, filePath):
    
    processFlag = False
    upgradeErrMsg = ""
    
    #上传升级包
    processRet = uploadHotPatchPackage(dataDict, filePath)
    if not processRet[0]:
        processFlag = False
        upgradeErrMsg = processRet[1]
        return (processFlag, upgradeErrMsg)

    #获取激活方式
    processRet = checkActiveMode(dataDict)
    if not processRet[0]:
        processFlag = False
        upgradeErrMsg = processRet[1]
        return (processFlag, upgradeErrMsg)
    
    #升级热补丁
    processRet = installHotPatchPackage(dataDict)
    if not processRet[0]:
        processFlag = False
        upgradeErrMsg = processRet[1]
        return (processFlag, upgradeErrMsg)
    
    #安装热补丁成功
    return (True, "")

# 使用TLV命令安装热补丁 20131130 modified End

# *************************************************************#
# 函数名称: upgradeProcessSpecial
# 功能说明: 特殊热补丁升级包的升级执行函数
# 其 他   :  无
# *************************************************************#
def upgradeProcessSpecial(dataDict, filePath):
    
    resource = dataDict["resource"] 
    tlvCon = dataDict.get("tlv")
    sftp = dataDict.get("sftp")
    devUploadPath = r"/home/permitdir/export_import"
    
    processFlag = False
    upgradeErrMsg = ""
    
    shellFile = "install_patch.sh"
    patchName = "patch.tgz"

    extractPath = filePath[0:-4]
    
    #工具暂时不支持特殊热补丁包的升级
    upgradeErrMsg = "Current tool does not support to install the special hot patch."
    return (processFlag, upgradeErrMsg) 
    
    """将文件解压到本地,并上传到阵列"""
    try:
        tarObject = tarfile.open(filePath, "r:gz")
        limit = UnZipLimit()
        for tarSubFile in tarObject:
            if tarSubFile.name in [shellFile, patchName]:
                limit.increase_file_size(tarSubFile.size)
                tar_safe_name = get_safe_entry_name(tarSubFile.name)
                tarObject.extract(tar_safe_name, extractPath)
                #将shell脚本和热补丁传入阵列
                uploadFileName = extractPath + os.sep + tar_safe_name
                sftp.putFile(uploadFileName, devUploadPath)
            if limit.is_file_size_over_limit():
                upgradeErrMsg = resource.get("1004") + resource.get("1006")
                return False, upgradeErrMsg
        tarObject.close()
    except Exception, e:
        processFlag = False
        upgradeErrMsg = resource.get("1004") + resource.get("1006")
        return (processFlag, upgradeErrMsg)
    finally:
        shutil.rmtree(extractPath, ignore_errors = True)
    
    """发送TLV命令，执行shell脚本"""
    rec = "execute the shell script success."
    if re.search("success", rec, re.IGNORECASE):
        processFlag = True
        upgradeErrMsg = ""
        return (processFlag, upgradeErrMsg)
    else:
        processFlag = False
        upgradeErrMsg = resource.get("2012")
        return (processFlag, upgradeErrMsg)

    return (processFlag, upgradeErrMsg)  

# 补丁工具代码流程优化 added 20131112 Begin
# *************************************************************#
# 函数名称: SetIPTVDeviceSlowDiskPolicy
# 功能说明: 设置IPTV设备的慢盘策略参数
# 其 他   :  无
# *************************************************************#
def SetIPTVDeviceSlowDiskPolicy(dataDict):
    
    ssh = dataDict['ssh']
    resource = dataDict["resource"]
    logger = dataDict["logger"]

    ifIptvDevice = False 
    ifNeedChange = False  
    processFlag = False
    upgradeErrMsg = ""
    IOAsvcTimeData = ""

    #IPTV设备才需要设定慢盘参数(Cli模式下可以查询)
    iRet = common.checkIfIPTVDevice(ssh)
    processFlag = iRet[0]
    ifIptvDevice = iRet[1]
    #获取信息失败，返回
    if not processFlag:
        upgradeErrMsg = resource.get("2015")
        return (processFlag, upgradeErrMsg)
    #非IPTV设备直接返回
    if not ifIptvDevice:
        logger.info("Current system is not IPTV Service, do not need to be set.")
        return (processFlag, upgradeErrMsg)
    logger.info("Current system is IPTV Service, need to be set.")
    
    #切换到developer模式
    flag = common.changeCli2Developer(dataDict)
    if not flag:
        processFlag = False
        upgradeErrMsg = resource.get("2014")
        return (processFlag, upgradeErrMsg)
    
    #是否需要更改慢盘策略
    iRet = common.checkIfNeedChangSlowDiskPolicy(ssh)
    processFlag = iRet[0]
    ifNeedChange = iRet[1]
    #获取信息失败，返回
    if not processFlag:
        upgradeErrMsg = resource.get("2016")
        common.changeAnyModel2Cli(ssh)
        return (processFlag, upgradeErrMsg)
    #慢盘策略不需要修改直接返回
    if not ifNeedChange:
        logger.info("Current IPTV device's slow disk policy has been changed, do not need to be set again.")
        common.changeAnyModel2Cli(ssh)
        return (processFlag, upgradeErrMsg)
    logger.info("Current IPTV device's slow disk policy has not been changed, need to be set.")

    #设置慢盘参数
    setPolicyTmp = ssh.execCmd("chgslowdiskpolicy -sv 70")
    if not re.search("command operates successfully", setPolicyTmp, re.IGNORECASE): 
        logger.error("Change the slow disk policy failed.")
        common.changeAnyModel2Cli(ssh)
        processFlag = False
        pgradeErrMsg = resource.get("2017")
        return (processFlag, upgradeErrMsg)
    
    #检验设置参数是否成功
    PolicyTmp = ssh.execCmd("showslowdiskpolicy")
    #命令执行失败
    if not re.search("Detect Slowdisk Policy", PolicyTmp, re.IGNORECASE):
        processFlag = False
        pgradeErrMsg = resource.get("2016")
        return (processFlag, ifNeedChange)

    for line in PolicyTmp.splitlines():
        field = line.split("|")
        #获取参数值
        if line.find("IO Asvc Time(ms)") >= 0:
            IOAsvcTimeData = field[1].strip()
            break
        else:
            continue
    
    #参数不为70，则修改失败
    if IOAsvcTimeData != "70":
        processFlag = False
        upgradeErrMsg = resource.get("2017")
        logger.error("Change the slow disk policy failed.")
    else:
        processFlag = True
        logger.info("Change the slow disk policy succeed.")
    
    #切换回cli模式，返回
    common.changeAnyModel2Cli(ssh)
    return (processFlag, upgradeErrMsg)

# 补丁工具代码流程优化 added 20131112 End

# *************************************************************#
# 函数名称: execute
# 功能说明: 热补丁升级接口
# 其 他   :  无
# *************************************************************#
def execute(dataDict):
    
    hotPatchTgzPkgName = dataDict['packagePath']
    lang = dataDict['lang']
    logger = dataDict['logger']
    ssh = dataDict['ssh']
    
    """解析resource文件并保存"""
    resource = resourceParse.execute(lang)
    dataDict["resource"] = resource
        
    processFlag = True
    upgradeErrMsg = ''
    
    hotPatchPkgVer = ""
    hotPatchSupportSysVer = ""
    hotPatchVerCheck = ""
    hotPatchSpcVer = ""
    specialPkgFlag = False
    
    # 补丁工具代码流程优化 modified 20131112 Begin
    #查询设备类型
    DeviceType = common.getCurDeviceType(ssh)
    #查询设备类型失败
    if DeviceType == "":
        processFlag = False
        upgradeErrMsg = resource.get('2000')
        return (processFlag, upgradeErrMsg, None)

    #获取当前系统SPC版本号
    curSpcVer = common.getCurSystemVersion(ssh)
    #查询系统版本号失败
    if curSpcVer == "":
        processFlag = False
        upgradeErrMsg = resource.get("2001")
        return (processFlag, upgradeErrMsg, None)
    
    logger.info("current system SPC version:" + str(curSpcVer))

    #通过解析versionsconf文件获取当前系统对应的热补丁版本号
    hotPatchVersionCheck = getCurSPCVerVerInfo(DeviceType, curSpcVer, logger)
    logger.info("Get current system related hotpatch version:" + str(hotPatchVersionCheck))
    if hotPatchVersionCheck == "":
        processFlag = False
        upgradeErrMsg = resource.get("2007")
        return (processFlag, upgradeErrMsg, None)

    #获取此热补丁升级包的版本号：S2600T V100R005C00SPH301（特殊热补丁包可能包含多个版本号）
    dataDictTmp = {}
    parseResults = {}
    dataDictTmp["parsePath"] = hotPatchTgzPkgName
    dataDictTmp["lang"] = lang
    dataDictTmp["logger"] = logger
    iRet = filePathParse.execute(dataDictTmp)
    
    #获取特殊补丁包flag
    specialPkgFlag = dataDictTmp["SpecialPkg"]
    processFlag = iRet[0]
    parseResults = iRet[2]
    if processFlag != True:
        upgradeErrMsg = iRet[1]
        return (processFlag, upgradeErrMsg, None)
    
    #查看当前设备对应的热补丁版本是否与传入热补丁包相匹配
    checkFlag = False
    for key in parseResults:
        if hotPatchVersionCheck == key:
            checkFlag = True
            break

    if checkFlag == False:
        processFlag = False
        upgradeErrMsg = resource.get("2008")
        return (processFlag, upgradeErrMsg, None)
    
    #查询设备当前已安装热补丁版本号
    iRet = common.getCurHotPatchVersion(ssh, resource)
    upgradeErrMsg = iRet[1]
    #获取补丁失败or当前版本不支持热补丁，报错返回
    if not iRet[0] or upgradeErrMsg == resource.get('2002'):
        return (False, upgradeErrMsg, None)
    #获取热补丁版本号
    curHotPatchVerOld = iRet[2]

    #升级热补丁前的特殊操作
    dataDict["curHotPatchVer"] = curHotPatchVerOld
    dataDict["installHotPatchVer"] = hotPatchVersionCheck
    dataDict["curSpcVerBefore"] = curSpcVer
    iRet = specialProcessBeforeInstall(dataDict)
    if False == iRet[0]:
        processFlag = False
        upgradeErrMsg = iRet[1]
        return (processFlag, upgradeErrMsg, None)

    #校验成功，调用升级流程
    iRet = upgradeProcess(dataDict, hotPatchTgzPkgName, specialPkgFlag)
    if False == iRet[0]:
        processFlag = False
        upgradeErrMsg = iRet[1]
        return (processFlag, upgradeErrMsg, None)

    #查询设备当前已安装热补丁版本号
    iRet = common.getCurHotPatchVersion(ssh, resource)
    upgradeErrMsg = iRet[1]
    #获取补丁失败or当前版本不支持热补丁，报错返回
    if not iRet[0] or upgradeErrMsg == resource.get('2002'):
        return (False, upgradeErrMsg, None)

    #获取热补丁版本号
    curHotPatchVer = iRet[2]
    dataDict["curHotPatchVer"] = curHotPatchVer
    
    hotPatchVerCheck = hotPatchVersionCheck[-6:]
    logger.info("Hotpatch Verify version:" + str(hotPatchVerCheck))
    logger.info("Current Hotpatch version:" + str(curHotPatchVer))
    #热补丁版本号校验
    if curHotPatchVer == "" or not re.search(hotPatchVerCheck, curHotPatchVer, re.IGNORECASE):
        processFlag = False
        upgradeErrMsg = resource.get("1005")
        return (processFlag, upgradeErrMsg, None)
    else:
        processFlag = True
        upgradeErrMsg = ""
    
    # S3900热补丁SPHh02替换SPHh01 20131130 modified Begin
    #S3900设备，安装了SPHh01|SPH701两个补丁，需要设定IPTV服务的慢盘参数
    if DeviceType in ["S3900-M200", "S3900-M300", "S5500T"]:
        #设计修改参数的两个系统版本
        if curSpcVer in ["V100R005C00SPC700", "V100R002C00SPCh00"]:           
            #SPH701或SPHh01热补丁需要做特殊处理
            logger.info("Current system need to set slow disk policy.")

            iRet = SetIPTVDeviceSlowDiskPolicy(dataDict)
            processFlag = iRet[0]
            upgradeErrMsg = iRet[1]
    # S3900热补丁SPHh02替换SPHh01 20131130 modified End
            
    #升级结果返回
    return (processFlag, upgradeErrMsg, None)
    # 补丁工具代码流程优化 modified 20131112 End
