Check In tool source code based on Build tool project revision r1655.
git-svn-id: https://edk2.svn.sourceforge.net/svnroot/edk2/trunk/edk2@8964 6f19259b-4bc3-4df7-8a09-765794883524
This commit is contained in:
329
BaseTools/Source/Python/Ecc/Ecc.py
Normal file
329
BaseTools/Source/Python/Ecc/Ecc.py
Normal file
@ -0,0 +1,329 @@
|
||||
## @file
|
||||
# This file is used to be the main entrance of ECC tool
|
||||
#
|
||||
# Copyright (c) 2009, Intel Corporation
|
||||
# All rights reserved. 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.
|
||||
#
|
||||
|
||||
##
|
||||
# Import Modules
|
||||
#
|
||||
import os, time, glob, sys
|
||||
import Common.EdkLogger as EdkLogger
|
||||
import Database
|
||||
import EccGlobalData
|
||||
from MetaDataParser import *
|
||||
from optparse import OptionParser
|
||||
from Configuration import Configuration
|
||||
from Check import Check
|
||||
from Common.InfClassObject import Inf
|
||||
from Common.DecClassObject import Dec
|
||||
from Common.DscClassObject import Dsc
|
||||
from Common.FdfClassObject import Fdf
|
||||
from Common.String import NormPath
|
||||
from Common import BuildToolError
|
||||
import c
|
||||
from Exception import *
|
||||
|
||||
## Ecc
|
||||
#
|
||||
# This class is used to define Ecc main entrance
|
||||
#
|
||||
# @param object: Inherited from object class
|
||||
#
|
||||
class Ecc(object):
|
||||
def __init__(self):
|
||||
# Version and Copyright
|
||||
self.VersionNumber = "0.01"
|
||||
self.Version = "%prog Version " + self.VersionNumber
|
||||
self.Copyright = "Copyright (c) 2009, Intel Corporation All rights reserved."
|
||||
|
||||
self.InitDefaultConfigIni()
|
||||
self.OutputFile = 'output.txt'
|
||||
self.ReportFile = 'Report.csv'
|
||||
self.ExceptionFile = 'exception.xml'
|
||||
self.IsInit = True
|
||||
self.ScanSourceCode = True
|
||||
self.ScanMetaData = True
|
||||
|
||||
# Parse the options and args
|
||||
self.ParseOption()
|
||||
|
||||
# Generate checkpoints list
|
||||
EccGlobalData.gConfig = Configuration(self.ConfigFile)
|
||||
|
||||
# Generate exception list
|
||||
EccGlobalData.gException = ExceptionCheck(self.ExceptionFile)
|
||||
|
||||
# Init Ecc database
|
||||
EccGlobalData.gDb = Database.Database(Database.DATABASE_PATH)
|
||||
EccGlobalData.gDb.InitDatabase(self.IsInit)
|
||||
|
||||
# Build ECC database
|
||||
self.BuildDatabase()
|
||||
|
||||
# Start to check
|
||||
self.Check()
|
||||
|
||||
# Show report
|
||||
self.GenReport()
|
||||
|
||||
# Close Database
|
||||
EccGlobalData.gDb.Close()
|
||||
|
||||
def InitDefaultConfigIni(self):
|
||||
paths = map(lambda p: os.path.join(p, 'Ecc', 'config.ini'), sys.path)
|
||||
paths = (os.path.realpath('config.ini'),) + tuple(paths)
|
||||
for path in paths:
|
||||
if os.path.exists(path):
|
||||
self.ConfigFile = path
|
||||
return
|
||||
self.ConfigFile = 'config.ini'
|
||||
|
||||
## BuildDatabase
|
||||
#
|
||||
# Build the database for target
|
||||
#
|
||||
def BuildDatabase(self):
|
||||
# Clean report table
|
||||
EccGlobalData.gDb.TblReport.Drop()
|
||||
EccGlobalData.gDb.TblReport.Create()
|
||||
|
||||
# Build database
|
||||
if self.IsInit:
|
||||
if self.ScanSourceCode:
|
||||
EdkLogger.quiet("Building database for source code ...")
|
||||
c.CollectSourceCodeDataIntoDB(EccGlobalData.gTarget)
|
||||
if self.ScanMetaData:
|
||||
EdkLogger.quiet("Building database for source code done!")
|
||||
self.BuildMetaDataFileDatabase()
|
||||
|
||||
EccGlobalData.gIdentifierTableList = GetTableList((MODEL_FILE_C, MODEL_FILE_H), 'Identifier', EccGlobalData.gDb)
|
||||
|
||||
## BuildMetaDataFileDatabase
|
||||
#
|
||||
# Build the database for meta data files
|
||||
#
|
||||
def BuildMetaDataFileDatabase(self):
|
||||
EdkLogger.quiet("Building database for meta data files ...")
|
||||
Op = open(EccGlobalData.gConfig.MetaDataFileCheckPathOfGenerateFileList, 'w+')
|
||||
#SkipDirs = Read from config file
|
||||
SkipDirs = EccGlobalData.gConfig.SkipDirList
|
||||
for Root, Dirs, Files in os.walk(EccGlobalData.gTarget):
|
||||
for Dir in Dirs:
|
||||
if Dir.upper() in SkipDirs:
|
||||
Dirs.remove(Dir)
|
||||
|
||||
for Dir in Dirs:
|
||||
Dirname = os.path.join(Root, Dir)
|
||||
if os.path.islink(Dirname):
|
||||
Dirname = os.path.realpath(Dirname)
|
||||
if os.path.isdir(Dirname):
|
||||
# symlinks to directories are treated as directories
|
||||
Dirs.remove(Dir)
|
||||
Dirs.append(Dirname)
|
||||
|
||||
for File in Files:
|
||||
if len(File) > 4 and File[-4:].upper() == ".DEC":
|
||||
Filename = os.path.normpath(os.path.join(Root, File))
|
||||
EdkLogger.quiet("Parsing %s" % Filename)
|
||||
Op.write("%s\r" % Filename)
|
||||
Dec(Filename, True, True, EccGlobalData.gWorkspace, EccGlobalData.gDb)
|
||||
continue
|
||||
if len(File) > 4 and File[-4:].upper() == ".DSC":
|
||||
Filename = os.path.normpath(os.path.join(Root, File))
|
||||
EdkLogger.quiet("Parsing %s" % Filename)
|
||||
Op.write("%s\r" % Filename)
|
||||
Dsc(Filename, True, True, EccGlobalData.gWorkspace, EccGlobalData.gDb)
|
||||
continue
|
||||
if len(File) > 4 and File[-4:].upper() == ".INF":
|
||||
Filename = os.path.normpath(os.path.join(Root, File))
|
||||
EdkLogger.quiet("Parsing %s" % Filename)
|
||||
Op.write("%s\r" % Filename)
|
||||
Inf(Filename, True, True, EccGlobalData.gWorkspace, EccGlobalData.gDb)
|
||||
continue
|
||||
if len(File) > 4 and File[-4:].upper() == ".FDF":
|
||||
Filename = os.path.normpath(os.path.join(Root, File))
|
||||
EdkLogger.quiet("Parsing %s" % Filename)
|
||||
Op.write("%s\r" % Filename)
|
||||
Fdf(Filename, True, EccGlobalData.gWorkspace, EccGlobalData.gDb)
|
||||
continue
|
||||
Op.close()
|
||||
|
||||
# Commit to database
|
||||
EccGlobalData.gDb.Conn.commit()
|
||||
|
||||
EdkLogger.quiet("Building database for meta data files done!")
|
||||
|
||||
##
|
||||
#
|
||||
# Check each checkpoint
|
||||
#
|
||||
def Check(self):
|
||||
EdkLogger.quiet("Checking ...")
|
||||
EccCheck = Check()
|
||||
EccCheck.Check()
|
||||
EdkLogger.quiet("Checking done!")
|
||||
|
||||
##
|
||||
#
|
||||
# Generate the scan report
|
||||
#
|
||||
def GenReport(self):
|
||||
EdkLogger.quiet("Generating report ...")
|
||||
EccGlobalData.gDb.TblReport.ToCSV(self.ReportFile)
|
||||
EdkLogger.quiet("Generating report done!")
|
||||
|
||||
def GetRealPathCase(self, path):
|
||||
TmpPath = path.rstrip(os.sep)
|
||||
PathParts = TmpPath.split(os.sep)
|
||||
if len(PathParts) == 0:
|
||||
return path
|
||||
if len(PathParts) == 1:
|
||||
if PathParts[0].strip().endswith(':'):
|
||||
return PathParts[0].upper()
|
||||
# Relative dir, list . current dir
|
||||
Dirs = os.listdir('.')
|
||||
for Dir in Dirs:
|
||||
if Dir.upper() == PathParts[0].upper():
|
||||
return Dir
|
||||
|
||||
if PathParts[0].strip().endswith(':'):
|
||||
PathParts[0] = PathParts[0].upper()
|
||||
ParentDir = PathParts[0]
|
||||
RealPath = ParentDir
|
||||
if PathParts[0] == '':
|
||||
RealPath = os.sep
|
||||
ParentDir = os.sep
|
||||
|
||||
PathParts.remove(PathParts[0]) # need to remove the parent
|
||||
for Part in PathParts:
|
||||
Dirs = os.listdir(ParentDir + os.sep)
|
||||
for Dir in Dirs:
|
||||
if Dir.upper() == Part.upper():
|
||||
RealPath += os.sep
|
||||
RealPath += Dir
|
||||
break
|
||||
ParentDir += os.sep
|
||||
ParentDir += Dir
|
||||
|
||||
return RealPath
|
||||
|
||||
## ParseOption
|
||||
#
|
||||
# Parse options
|
||||
#
|
||||
def ParseOption(self):
|
||||
EdkLogger.quiet("Loading ECC configuration ... done")
|
||||
(Options, Target) = self.EccOptionParser()
|
||||
|
||||
# Check workspace envirnoment
|
||||
if "WORKSPACE" not in os.environ:
|
||||
EdkLogger.error("ECC", BuildToolError.ATTRIBUTE_NOT_AVAILABLE, "Environment variable not found",
|
||||
ExtraData="WORKSPACE")
|
||||
else:
|
||||
EccGlobalData.gWorkspace = os.path.normpath(os.getenv("WORKSPACE"))
|
||||
if not os.path.exists(EccGlobalData.gWorkspace):
|
||||
EdkLogger.error("ECC", BuildToolError.FILE_NOT_FOUND, ExtraData="WORKSPACE = %s" % EccGlobalData.gWorkspace)
|
||||
os.environ["WORKSPACE"] = EccGlobalData.gWorkspace
|
||||
# Set log level
|
||||
self.SetLogLevel(Options)
|
||||
|
||||
# Set other options
|
||||
if Options.ConfigFile != None:
|
||||
self.ConfigFile = Options.ConfigFile
|
||||
if Options.OutputFile != None:
|
||||
self.OutputFile = Options.OutputFile
|
||||
if Options.ReportFile != None:
|
||||
self.ReportFile = Options.ReportFile
|
||||
if Options.Target != None:
|
||||
if not os.path.isdir(Options.Target):
|
||||
EdkLogger.error("ECC", BuildToolError.OPTION_VALUE_INVALID, ExtraData="Target [%s] does NOT exist" % Options.Target)
|
||||
else:
|
||||
EccGlobalData.gTarget = self.GetRealPathCase(os.path.normpath(Options.Target))
|
||||
else:
|
||||
EdkLogger.warn("Ecc", EdkLogger.ECC_ERROR, "The target source tree was not specified, using current WORKSPACE instead!")
|
||||
EccGlobalData.gTarget = os.path.normpath(os.getenv("WORKSPACE"))
|
||||
if Options.keepdatabase != None:
|
||||
self.IsInit = False
|
||||
if Options.metadata != None and Options.sourcecode != None:
|
||||
EdkLogger.error("ECC", BuildToolError.OPTION_CONFLICT, ExtraData="-m and -s can't be specified at one time")
|
||||
if Options.metadata != None:
|
||||
self.ScanSourceCode = False
|
||||
if Options.sourcecode != None:
|
||||
self.ScanMetaData = False
|
||||
|
||||
## SetLogLevel
|
||||
#
|
||||
# Set current log level of the tool based on args
|
||||
#
|
||||
# @param Option: The option list including log level setting
|
||||
#
|
||||
def SetLogLevel(self, Option):
|
||||
if Option.verbose != None:
|
||||
EdkLogger.SetLevel(EdkLogger.VERBOSE)
|
||||
elif Option.quiet != None:
|
||||
EdkLogger.SetLevel(EdkLogger.QUIET)
|
||||
elif Option.debug != None:
|
||||
EdkLogger.SetLevel(Option.debug + 1)
|
||||
else:
|
||||
EdkLogger.SetLevel(EdkLogger.INFO)
|
||||
|
||||
## Parse command line options
|
||||
#
|
||||
# Using standard Python module optparse to parse command line option of this tool.
|
||||
#
|
||||
# @retval Opt A optparse.Values object containing the parsed options
|
||||
# @retval Args Target of build command
|
||||
#
|
||||
def EccOptionParser(self):
|
||||
Parser = OptionParser(description = self.Copyright, version = self.Version, prog = "Ecc.exe", usage = "%prog [options]")
|
||||
Parser.add_option("-t", "--target sourcepath", action="store", type="string", dest='Target',
|
||||
help="Check all files under the target workspace.")
|
||||
Parser.add_option("-c", "--config filename", action="store", type="string", dest="ConfigFile",
|
||||
help="Specify a configuration file. Defaultly use config.ini under ECC tool directory.")
|
||||
Parser.add_option("-o", "--outfile filename", action="store", type="string", dest="OutputFile",
|
||||
help="Specify the name of an output file, if and only if one filename was specified.")
|
||||
Parser.add_option("-r", "--reportfile filename", action="store", type="string", dest="ReportFile",
|
||||
help="Specify the name of an report file, if and only if one filename was specified.")
|
||||
Parser.add_option("-m", "--metadata", action="store_true", type=None, help="Only scan meta-data files information if this option is specified.")
|
||||
Parser.add_option("-s", "--sourcecode", action="store_true", type=None, help="Only scan source code files information if this option is specified.")
|
||||
Parser.add_option("-k", "--keepdatabase", action="store_true", type=None, help="The existing Ecc database will not be cleaned except report information if this option is specified.")
|
||||
Parser.add_option("-l", "--log filename", action="store", dest="LogFile", help="""If specified, the tool should emit the changes that
|
||||
were made by the tool after printing the result message.
|
||||
If filename, the emit to the file, otherwise emit to
|
||||
standard output. If no modifications were made, then do not
|
||||
create a log file, or output a log message.""")
|
||||
Parser.add_option("-q", "--quiet", action="store_true", type=None, help="Disable all messages except FATAL ERRORS.")
|
||||
Parser.add_option("-v", "--verbose", action="store_true", type=None, help="Turn on verbose output with informational messages printed, "\
|
||||
"including library instances selected, final dependency expression, "\
|
||||
"and warning messages, etc.")
|
||||
Parser.add_option("-d", "--debug", action="store", type="int", help="Enable debug messages at specified level.")
|
||||
|
||||
(Opt, Args)=Parser.parse_args()
|
||||
|
||||
return (Opt, Args)
|
||||
|
||||
##
|
||||
#
|
||||
# This acts like the main() function for the script, unless it is 'import'ed into another
|
||||
# script.
|
||||
#
|
||||
if __name__ == '__main__':
|
||||
# Initialize log system
|
||||
EdkLogger.Initialize()
|
||||
EdkLogger.IsRaiseError = False
|
||||
EdkLogger.quiet(time.strftime("%H:%M:%S, %b.%d %Y ", time.localtime()) + "[00:00]" + "\n")
|
||||
|
||||
StartTime = time.clock()
|
||||
Ecc = Ecc()
|
||||
FinishTime = time.clock()
|
||||
|
||||
BuildDuration = time.strftime("%M:%S", time.gmtime(int(round(FinishTime - StartTime))))
|
||||
EdkLogger.quiet("\n%s [%s]" % (time.strftime("%H:%M:%S, %b.%d %Y", time.localtime()), BuildDuration))
|
Reference in New Issue
Block a user