## @file
# This file is used to provide method for process AsBuilt INF file. It will consumed by InfParser
#
# Copyright (c) 2011 - 2018, Intel Corporation. All rights reserved.<BR>
#
# This program and the accompanying materials are licensed and made available
# under the terms and conditions of the BSD License which accompanies this
# distribution. The full text of the license may be found at
# http://opensource.org/licenses/bsd-license.php
#
# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
'''
InfAsBuiltProcess
'''
## Import modules
#

import os
import re
from Library import GlobalData
import Logger.Log as Logger
from Logger import StringTable as ST
from Logger import ToolError

from Library.StringUtils import GetSplitValueList
from Library.Misc import GetHelpStringByRemoveHashKey
from Library.Misc import ValidFile
from Library.Misc import ProcessLineExtender
from Library.ParserValidate import IsValidPath
from Library.Parsing import MacroParser
from Parser.InfParserMisc import InfExpandMacro

from Library import DataType as DT

## GetLibInstanceInfo
#
# Get the information from Library Instance INF file.
#
# @param string.  A string start with # and followed by INF file path
# @param WorkSpace. The WorkSpace directory used to combined with INF file path.
#
# @return GUID, Version
def GetLibInstanceInfo(String, WorkSpace, LineNo, CurrentInfFileName):

    FileGuidString = ""
    VerString = ""

    OriginalString = String
    String = String.strip()
    if not String:
        return None, None
    #
    # Remove "#" characters at the beginning
    #
    String = GetHelpStringByRemoveHashKey(String)
    String = String.strip()

    #
    # To deal with library instance specified by GUID and version
    #
    RegFormatGuidPattern = re.compile("\s*([0-9a-fA-F]){8}-"
                                       "([0-9a-fA-F]){4}-"
                                       "([0-9a-fA-F]){4}-"
                                       "([0-9a-fA-F]){4}-"
                                       "([0-9a-fA-F]){12}\s*")
    VersionPattern = re.compile('[\t\s]*\d+(\.\d+)?[\t\s]*')
    GuidMatchedObj = RegFormatGuidPattern.search(String)

    if String.upper().startswith('GUID') and GuidMatchedObj and 'Version' in String:
        VersionStr = String[String.upper().find('VERSION') + 8:]
        VersionMatchedObj = VersionPattern.search(VersionStr)
        if VersionMatchedObj:
            Guid = GuidMatchedObj.group().strip()
            Version = VersionMatchedObj.group().strip()
            return Guid, Version

    #
    # To deal with library instance specified by file name
    #
    FileLinesList = GetFileLineContent(String, WorkSpace, LineNo, OriginalString)


    ReFindFileGuidPattern = re.compile("^\s*FILE_GUID\s*=.*$")
    ReFindVerStringPattern = re.compile("^\s*VERSION_STRING\s*=.*$")

    for Line in FileLinesList:
        if ReFindFileGuidPattern.match(Line):
            FileGuidString = Line
        if ReFindVerStringPattern.match(Line):
            VerString = Line

    if FileGuidString:
        FileGuidString = GetSplitValueList(FileGuidString, '=', 1)[1]
    if VerString:
        VerString = GetSplitValueList(VerString, '=', 1)[1]

    return FileGuidString, VerString

## GetPackageListInfo
#
# Get the package information from INF file.
#
# @param string.  A string start with # and followed by INF file path
# @param WorkSpace. The WorkSpace directory used to combined with INF file path.
#
# @return GUID, Version
def GetPackageListInfo(FileNameString, WorkSpace, LineNo):
    PackageInfoList = []
    DefineSectionMacros = {}
    PackageSectionMacros = {}

    FileLinesList = GetFileLineContent(FileNameString, WorkSpace, LineNo, '')

    RePackageHeader = re.compile('^\s*\[Packages.*\].*$')
    ReDefineHeader = re.compile('^\s*\[Defines].*$')

    PackageHederFlag = False
    DefineHeaderFlag = False
    LineNo = -1
    for Line in FileLinesList:
        LineNo += 1
        Line = Line.strip()

        if Line.startswith('['):
            PackageHederFlag = False
            DefineHeaderFlag = False

        if Line.startswith("#"):
            continue

        if not Line:
            continue

        #
        # Found [Packages] section
        #
        if RePackageHeader.match(Line):
            PackageHederFlag = True
            continue

        #
        # Found [Define] section
        #
        if ReDefineHeader.match(Line):
            DefineHeaderFlag = True
            continue

        if DefineHeaderFlag:
            #
            # Find Macro
            #
            Name, Value = MacroParser((Line, LineNo),
                                      FileNameString,
                                      DT.MODEL_META_DATA_HEADER,
                                      DefineSectionMacros)

            if Name is not None:
                DefineSectionMacros[Name] = Value
                continue

        if PackageHederFlag:

            #
            # Find Macro
            #
            Name, Value = MacroParser((Line, LineNo),
                                      FileNameString,
                                      DT.MODEL_META_DATA_PACKAGE,
                                      DefineSectionMacros)
            if Name is not None:
                PackageSectionMacros[Name] = Value
                continue

            #
            # Replace with Local section Macro and [Defines] section Macro.
            #
            Line = InfExpandMacro(Line, (FileNameString, Line, LineNo), DefineSectionMacros, PackageSectionMacros, True)

            Line = GetSplitValueList(Line, "#", 1)[0]
            Line = GetSplitValueList(Line, "|", 1)[0]
            PackageInfoList.append(Line)

    return PackageInfoList

def GetFileLineContent(FileName, WorkSpace, LineNo, OriginalString):

    if not LineNo:
        LineNo = -1

    #
    # Validate file name exist.
    #
    FullFileName = os.path.normpath(os.path.realpath(os.path.join(WorkSpace, FileName)))
    if not (ValidFile(FullFileName)):
        return []

    #
    # Validate file exist/format.
    #
    if not IsValidPath(FileName, WorkSpace):
        return []

    FileLinesList = []

    try:
        FullFileName = FullFileName.replace('\\', '/')
        Inputfile = open(FullFileName, "r")
        try:
            FileLinesList = Inputfile.readlines()
        except BaseException:
            Logger.Error("InfParser", ToolError.FILE_READ_FAILURE, ST.ERR_FILE_OPEN_FAILURE, File=FullFileName)
        finally:
            Inputfile.close()
    except BaseException:
        Logger.Error("InfParser",
                     ToolError.FILE_READ_FAILURE,
                     ST.ERR_FILE_OPEN_FAILURE,
                     File=FullFileName)

    FileLinesList = ProcessLineExtender(FileLinesList)

    return FileLinesList

##
# Get all INF files from current workspace
#
#
def GetInfsFromWorkSpace(WorkSpace):
    InfFiles = []
    for top, dirs, files in os.walk(WorkSpace):
        dirs = dirs # just for pylint
        for File in files:
            if File.upper().endswith(".INF"):
                InfFiles.append(os.path.join(top, File))

    return InfFiles

##
# Get GUID and version from library instance file
#
#
def GetGuidVerFormLibInstance(Guid, Version, WorkSpace, CurrentInfFileName):
    for InfFile in GetInfsFromWorkSpace(WorkSpace):
        try:
            if InfFile.strip().upper() == CurrentInfFileName.strip().upper():
                continue
            InfFile = InfFile.replace('\\', '/')
            if InfFile not in GlobalData.gLIBINSTANCEDICT:
                InfFileObj = open(InfFile, "r")
                GlobalData.gLIBINSTANCEDICT[InfFile] = InfFileObj
            else:
                InfFileObj = GlobalData.gLIBINSTANCEDICT[InfFile]

        except BaseException:
            Logger.Error("InfParser",
                         ToolError.FILE_READ_FAILURE,
                         ST.ERR_FILE_OPEN_FAILURE,
                         File=InfFile)
        try:
            FileLinesList = InfFileObj.readlines()
            FileLinesList = ProcessLineExtender(FileLinesList)

            ReFindFileGuidPattern = re.compile("^\s*FILE_GUID\s*=.*$")
            ReFindVerStringPattern = re.compile("^\s*VERSION_STRING\s*=.*$")

            for Line in FileLinesList:
                if ReFindFileGuidPattern.match(Line):
                    FileGuidString = Line
                if ReFindVerStringPattern.match(Line):
                    VerString = Line

            if FileGuidString:
                FileGuidString = GetSplitValueList(FileGuidString, '=', 1)[1]
            if VerString:
                VerString = GetSplitValueList(VerString, '=', 1)[1]

            if FileGuidString.strip().upper() == Guid.upper() and \
                VerString.strip().upper() == Version.upper():
                return Guid, Version

        except BaseException:
            Logger.Error("InfParser", ToolError.FILE_READ_FAILURE, ST.ERR_FILE_OPEN_FAILURE, File=InfFile)
        finally:
            InfFileObj.close()

    return '', ''


