## @file\r
# This file is used to be the c coding style checking of ECC tool\r
#\r
-# Copyright (c) 2009 - 2010, Intel Corporation. All rights reserved.<BR>\r
+# Copyright (c) 2009 - 2017, Intel Corporation. All rights reserved.<BR>\r
# This program and the accompanying materials\r
# are licensed and made available under the terms and conditions of the BSD License\r
# which accompanies this distribution. The full text of the license may be found at\r
#\r
\r
import sys\r
-import os\r
+import Common.LongFilePathOs as os\r
import re\r
import string\r
import CodeFragmentCollector\r
for Part in MsgPartList:\r
Msg += Part\r
Msg += ' '\r
- GetDB().TblReport.Insert(ErrorType, OtherMsg = Msg, BelongsToTable = TableName, BelongsToItem = ItemId)\r
+ GetDB().TblReport.Insert(ErrorType, OtherMsg=Msg, BelongsToTable=TableName, BelongsToItem=ItemId)\r
\r
def GetIdType(Str):\r
Type = DataClass.MODEL_UNKNOWN\r
def GetIdentifierList():\r
IdList = []\r
for comment in FileProfile.CommentList:\r
- IdComment = DataClass.IdentifierClass(-1, '', '', '', comment.Content, DataClass.MODEL_IDENTIFIER_COMMENT, -1, -1, comment.StartPos[0],comment.StartPos[1],comment.EndPos[0],comment.EndPos[1])\r
+ IdComment = DataClass.IdentifierClass(-1, '', '', '', comment.Content, DataClass.MODEL_IDENTIFIER_COMMENT, -1, -1, comment.StartPos[0], comment.StartPos[1], comment.EndPos[0], comment.EndPos[1])\r
IdList.append(IdComment)\r
\r
for pp in FileProfile.PPDirectiveList:\r
Type = GetIdType(pp.Content)\r
- IdPP = DataClass.IdentifierClass(-1, '', '', '', pp.Content, Type, -1, -1, pp.StartPos[0],pp.StartPos[1],pp.EndPos[0],pp.EndPos[1])\r
+ IdPP = DataClass.IdentifierClass(-1, '', '', '', pp.Content, Type, -1, -1, pp.StartPos[0], pp.StartPos[1], pp.EndPos[0], pp.EndPos[1])\r
IdList.append(IdPP)\r
\r
for pe in FileProfile.PredicateExpressionList:\r
- IdPE = DataClass.IdentifierClass(-1, '', '', '', pe.Content, DataClass.MODEL_IDENTIFIER_PREDICATE_EXPRESSION, -1, -1, pe.StartPos[0],pe.StartPos[1],pe.EndPos[0],pe.EndPos[1])\r
+ IdPE = DataClass.IdentifierClass(-1, '', '', '', pe.Content, DataClass.MODEL_IDENTIFIER_PREDICATE_EXPRESSION, -1, -1, pe.StartPos[0], pe.StartPos[1], pe.EndPos[0], pe.EndPos[1])\r
IdList.append(IdPE)\r
\r
FuncDeclPattern = GetFuncDeclPattern()\r
var.Modifier += ' ' + Name[LSBPos:]\r
Name = Name[0:LSBPos]\r
\r
- IdVar = DataClass.IdentifierClass(-1, var.Modifier, '', Name, (len(DeclList) > 1 and [DeclList[1]]or [''])[0], DataClass.MODEL_IDENTIFIER_VARIABLE, -1, -1, var.StartPos[0],var.StartPos[1], VarNameStartLine, VarNameStartColumn)\r
+ IdVar = DataClass.IdentifierClass(-1, var.Modifier, '', Name, (len(DeclList) > 1 and [DeclList[1]]or [''])[0], DataClass.MODEL_IDENTIFIER_VARIABLE, -1, -1, var.StartPos[0], var.StartPos[1], VarNameStartLine, VarNameStartColumn)\r
IdList.append(IdVar)\r
else:\r
DeclList = var.Declarator.split('=')\r
LSBPos = var.Declarator.find('[')\r
var.Modifier += ' ' + Name[LSBPos:]\r
Name = Name[0:LSBPos]\r
- IdVar = DataClass.IdentifierClass(-1, var.Modifier, '', Name, (len(DeclList) > 1 and [DeclList[1]]or [''])[0], DataClass.MODEL_IDENTIFIER_VARIABLE, -1, -1, var.StartPos[0],var.StartPos[1], VarNameStartLine, VarNameStartColumn)\r
+ IdVar = DataClass.IdentifierClass(-1, var.Modifier, '', Name, (len(DeclList) > 1 and [DeclList[1]]or [''])[0], DataClass.MODEL_IDENTIFIER_VARIABLE, -1, -1, var.StartPos[0], var.StartPos[1], VarNameStartLine, VarNameStartColumn)\r
IdList.append(IdVar)\r
\r
for enum in FileProfile.EnumerationDefinitionList:\r
LBPos = enum.Content.find('{')\r
RBPos = enum.Content.find('}')\r
Name = enum.Content[4:LBPos].strip()\r
- Value = enum.Content[LBPos+1:RBPos]\r
- IdEnum = DataClass.IdentifierClass(-1, '', '', Name, Value, DataClass.MODEL_IDENTIFIER_ENUMERATE, -1, -1, enum.StartPos[0],enum.StartPos[1],enum.EndPos[0],enum.EndPos[1])\r
+ Value = enum.Content[LBPos + 1:RBPos]\r
+ IdEnum = DataClass.IdentifierClass(-1, '', '', Name, Value, DataClass.MODEL_IDENTIFIER_ENUMERATE, -1, -1, enum.StartPos[0], enum.StartPos[1], enum.EndPos[0], enum.EndPos[1])\r
IdList.append(IdEnum)\r
\r
for su in FileProfile.StructUnionDefinitionList:\r
Value = ''\r
else:\r
Name = su.Content[SkipLen:LBPos].strip()\r
- Value = su.Content[LBPos:RBPos+1]\r
- IdPE = DataClass.IdentifierClass(-1, '', '', Name, Value, Type, -1, -1, su.StartPos[0],su.StartPos[1],su.EndPos[0],su.EndPos[1])\r
+ Value = su.Content[LBPos:RBPos + 1]\r
+ IdPE = DataClass.IdentifierClass(-1, '', '', Name, Value, Type, -1, -1, su.StartPos[0], su.StartPos[1], su.EndPos[0], su.EndPos[1])\r
IdList.append(IdPE)\r
\r
TdFuncPointerPattern = GetTypedefFuncPointerPattern()\r
if TdFuncPointerPattern.match(td.ToType):\r
Modifier = td.FromType\r
LBPos = td.ToType.find('(')\r
- TmpStr = td.ToType[LBPos+1:].strip()\r
+ TmpStr = td.ToType[LBPos + 1:].strip()\r
StarPos = TmpStr.find('*')\r
if StarPos != -1:\r
Modifier += ' ' + TmpStr[0:StarPos]\r
Value += Name[LBPos : RBPos + 1]\r
Name = Name[0 : LBPos]\r
\r
- IdTd = DataClass.IdentifierClass(-1, Modifier, '', Name, Value, DataClass.MODEL_IDENTIFIER_TYPEDEF, -1, -1, td.StartPos[0],td.StartPos[1],td.EndPos[0],td.EndPos[1])\r
+ IdTd = DataClass.IdentifierClass(-1, Modifier, '', Name, Value, DataClass.MODEL_IDENTIFIER_TYPEDEF, -1, -1, td.StartPos[0], td.StartPos[1], td.EndPos[0], td.EndPos[1])\r
IdList.append(IdTd)\r
\r
for funcCall in FileProfile.FunctionCallingList:\r
- IdFC = DataClass.IdentifierClass(-1, '', '', funcCall.FuncName, funcCall.ParamList, DataClass.MODEL_IDENTIFIER_FUNCTION_CALLING, -1, -1, funcCall.StartPos[0],funcCall.StartPos[1],funcCall.EndPos[0],funcCall.EndPos[1])\r
+ IdFC = DataClass.IdentifierClass(-1, '', '', funcCall.FuncName, funcCall.ParamList, DataClass.MODEL_IDENTIFIER_FUNCTION_CALLING, -1, -1, funcCall.StartPos[0], funcCall.StartPos[1], funcCall.EndPos[0], funcCall.EndPos[1])\r
IdList.append(IdFC)\r
return IdList\r
\r
def StripNonAlnumChars(Str):\r
StrippedStr = ''\r
for Char in Str:\r
- if Char.isalnum():\r
+ if Char.isalnum() or Char == '_':\r
StrippedStr += Char\r
return StrippedStr\r
\r
-def GetParamList(FuncDeclarator, FuncNameLine = 0, FuncNameOffset = 0):\r
+def GetParamList(FuncDeclarator, FuncNameLine=0, FuncNameOffset=0):\r
FuncDeclarator = StripComments(FuncDeclarator)\r
ParamIdList = []\r
#DeclSplitList = FuncDeclarator.split('(')\r
FuncNameStartColumn += 1\r
PreChar = FirstChar\r
\r
- FuncObj = DataClass.FunctionClass(-1, FuncDef.Declarator, FuncDef.Modifier, FuncName.strip(), '', FuncDef.StartPos[0],FuncDef.StartPos[1],FuncDef.EndPos[0],FuncDef.EndPos[1], FuncDef.LeftBracePos[0], FuncDef.LeftBracePos[1], -1, ParamIdList, [], FuncNameStartLine, FuncNameStartColumn)\r
+ FuncObj = DataClass.FunctionClass(-1, FuncDef.Declarator, FuncDef.Modifier, FuncName.strip(), '', FuncDef.StartPos[0], FuncDef.StartPos[1], FuncDef.EndPos[0], FuncDef.EndPos[1], FuncDef.LeftBracePos[0], FuncDef.LeftBracePos[1], -1, ParamIdList, [], FuncNameStartLine, FuncNameStartColumn)\r
FuncObjList.append(FuncObj)\r
\r
return FuncObjList\r
dirnames.append(Dirname)\r
\r
for f in filenames:\r
+ if f.lower() in EccGlobalData.gConfig.SkipFileList:\r
+ continue\r
+ collector = None\r
FullName = os.path.normpath(os.path.join(dirpath, f))\r
+ model = DataClass.MODEL_FILE_OTHERS\r
if os.path.splitext(f)[1] in ('.h', '.c'):\r
EdkLogger.info("Parsing " + FullName)\r
model = f.endswith('c') and DataClass.MODEL_FILE_C or DataClass.MODEL_FILE_H\r
collector.CleanFileProfileBuffer()\r
collector.ParseFileWithClearedPPDirective()\r
# collector.PrintFragments()\r
- BaseName = os.path.basename(f)\r
- DirName = os.path.dirname(FullName)\r
- Ext = os.path.splitext(f)[1].lstrip('.')\r
- ModifiedTime = os.path.getmtime(FullName)\r
- FileObj = DataClass.FileClass(-1, BaseName, Ext, DirName, FullName, model, ModifiedTime, GetFunctionList(), GetIdentifierList(), [])\r
- FileObjList.append(FileObj)\r
+ BaseName = os.path.basename(f)\r
+ DirName = os.path.dirname(FullName)\r
+ Ext = os.path.splitext(f)[1].lstrip('.')\r
+ ModifiedTime = os.path.getmtime(FullName)\r
+ FileObj = DataClass.FileClass(-1, BaseName, Ext, DirName, FullName, model, ModifiedTime, GetFunctionList(), GetIdentifierList(), [])\r
+ FileObjList.append(FileObj)\r
+ if collector:\r
collector.CleanFileProfileBuffer()\r
\r
if len(ParseErrorFileList) > 0:\r
\r
Db = GetDB()\r
for file in FileObjList:\r
- Db.InsertOneFile(file)\r
+ if file.ExtName.upper() not in ['INF', 'DEC', 'DSC', 'FDF']:\r
+ Db.InsertOneFile(file)\r
\r
Db.UpdateIdentifierBelongsToFunction()\r
\r
-def GetTableID(FullFileName, ErrorMsgList = None):\r
+def GetTableID(FullFileName, ErrorMsgList=None):\r
if ErrorMsgList == None:\r
ErrorMsgList = []\r
\r
from File\r
where FullPath like '%s'\r
""" % FullFileName\r
-\r
ResultSet = Db.TblFile.Exec(SqlStatement)\r
\r
FileID = -1\r
for Result in ResultSet:\r
if FileID != -1:\r
ErrorMsgList.append('Duplicate file ID found in DB for file %s' % FullFileName)\r
- return -2\r
+ return - 2\r
FileID = Result[0]\r
if FileID == -1:\r
ErrorMsgList.append('NO file ID found in DB for file %s' % FullFileName)\r
- return -1\r
+ return - 1\r
return FileID\r
\r
def GetIncludeFileList(FullFileName):\r
+ if os.path.splitext(FullFileName)[1].upper() not in ('.H'):\r
+ return []\r
IFList = IncludeFileListDict.get(FullFileName)\r
if IFList != None:\r
return IFList\r
while i < len(PES) - 1:\r
if (PES[i].isalnum() or PES[i] == '_' or PES[i] == '*') and LogicOpPos > PredicateBegin:\r
PredicateBegin = i\r
- if (PES[i] == '&' and PES[i+1] == '&') or (PES[i] == '|' and PES[i+1] == '|'):\r
+ if (PES[i] == '&' and PES[i + 1] == '&') or (PES[i] == '|' and PES[i + 1] == '|'):\r
LogicOpPos = i\r
Exp = PES[PredicateBegin:i].strip()\r
# Exp may contain '.' or '->'\r
PredicateList.append(Exp.rstrip(';').rstrip(')').strip())\r
return PredicateList\r
\r
-def GetCNameList(Lvalue, StarList = []):\r
+def GetCNameList(Lvalue, StarList=[]):\r
Lvalue += ' '\r
i = 0\r
SearchBegin = 0\r
VarEnd = i\r
i += 1\r
elif VarEnd != -1:\r
- VarList.append(Lvalue[VarStart:VarEnd+1])\r
+ VarList.append(Lvalue[VarStart:VarEnd + 1])\r
i += 1\r
break\r
else:\r
\r
return VarList\r
\r
-def SplitPredicateByOp(Str, Op, IsFuncCalling = False):\r
+def SplitPredicateByOp(Str, Op, IsFuncCalling=False):\r
\r
Name = Str.strip()\r
Value = None\r
return [Name]\r
\r
Name = Str[0:Index + IndexInRemainingStr].strip()\r
- Value = Str[Index+IndexInRemainingStr+len(Op):].strip().strip(')')\r
+ Value = Str[Index + IndexInRemainingStr + len(Op):].strip().strip(')')\r
return [Name, Value]\r
\r
TmpStr = Str.rstrip(';').rstrip(')')\r
if Index == -1:\r
return [Name]\r
\r
- if Str[Index - 1].isalnum() or Str[Index - 1].isspace() or Str[Index - 1] == ')':\r
+ if Str[Index - 1].isalnum() or Str[Index - 1].isspace() or Str[Index - 1] == ')' or Str[Index - 1] == ']':\r
Name = Str[0:Index].strip()\r
Value = Str[Index + len(Op):].strip()\r
return [Name, Value]\r
\r
def GetDataTypeFromModifier(ModifierStr):\r
MList = ModifierStr.split()\r
+ ReturnType = ''\r
for M in MList:\r
if M in EccGlobalData.gConfig.ModifierList:\r
- MList.remove(M)\r
+ continue\r
# remove array sufix\r
- if M.startswith('['):\r
- MList.remove(M)\r
-\r
- ReturnType = ''\r
- for M in MList:\r
+ if M.startswith('[') or M.endswith(']'):\r
+ continue\r
ReturnType += M + ' '\r
\r
ReturnType = ReturnType.strip()\r
DoubleSlashComment = False\r
Index += 1\r
# check for */ comment end\r
- elif InComment and not DoubleSlashComment and ListFromStr[Index] == '*' and ListFromStr[Index+1] == '/':\r
+ elif InComment and not DoubleSlashComment and ListFromStr[Index] == '*' and ListFromStr[Index + 1] == '/':\r
ListFromStr[Index] = ' '\r
Index += 1\r
ListFromStr[Index] = ' '\r
ListFromStr[Index] = ' '\r
Index += 1\r
# check for // comment\r
- elif ListFromStr[Index] == '/' and ListFromStr[Index+1] == '/' and ListFromStr[Index+2] != '\n':\r
+ elif ListFromStr[Index] == '/' and ListFromStr[Index + 1] == '/' and ListFromStr[Index + 2] != '\n':\r
InComment = True\r
DoubleSlashComment = True\r
\r
# check for /* comment start\r
- elif ListFromStr[Index] == '/' and ListFromStr[Index+1] == '*':\r
+ elif ListFromStr[Index] == '/' and ListFromStr[Index + 1] == '*':\r
ListFromStr[Index] = ' '\r
Index += 1\r
ListFromStr[Index] = ' '\r
\r
return None\r
\r
-def GetRealType(Type, TypedefDict, TargetType = None):\r
+def GetRealType(Type, TypedefDict, TargetType=None):\r
if TargetType != None and Type == TargetType:\r
return Type\r
while TypedefDict.get(Type):\r
return Type\r
return Type\r
\r
-def GetTypeInfo(RefList, Modifier, FullFileName, TargetType = None):\r
+def GetTypeInfo(RefList, Modifier, FullFileName, TargetType=None):\r
TypedefDict = GetTypedefDict(FullFileName)\r
SUDict = GetSUDict(FullFileName)\r
Type = GetDataTypeFromModifier(Modifier).replace('*', '').strip()\r
# we only want to check if it is a pointer\r
else:\r
Type = FromType\r
- if Type.find('*') != -1 and Index == len(RefList)-1:\r
+ if Type.find('*') != -1 and Index == len(RefList) - 1:\r
return Type\r
Type = FromType.split()[0]\r
\r
\r
return Type\r
\r
-def GetVarInfo(PredVarList, FuncRecord, FullFileName, IsFuncCall = False, TargetType = None, StarList = None):\r
+def GetVarInfo(PredVarList, FuncRecord, FullFileName, IsFuncCall=False, TargetType=None, StarList=None):\r
\r
PredVar = PredVarList[0]\r
FileID = GetTableID(FullFileName)\r
else:\r
TypeList = GetDataTypeFromModifier(Param.Modifier).split()\r
Type = TypeList[-1]\r
+ if Type == '*' and len(TypeList) >= 2:\r
+ Type = TypeList[-2]\r
if len(TypeList) > 1 and StarList != None:\r
for Star in StarList:\r
Type = Type.strip()\r
FuncName = Result[5]\r
if EccGlobalData.gException.IsException(ERROR_C_FUNCTION_LAYOUT_CHECK_RETURN_TYPE, FuncName):\r
continue\r
- Index = Result[0].find(TypeStart)\r
+ Result0 = Result[0]\r
+ if Result0.upper().startswith('STATIC'):\r
+ Result0 = Result0[6:].strip()\r
+ Index = Result0.find(TypeStart)\r
if Index != 0 or Result[3] != 0:\r
PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_RETURN_TYPE, '[%s] Return Type should appear at the start of line' % FuncName, FileTable, Result[1])\r
\r
FuncName = Result[5]\r
if EccGlobalData.gException.IsException(ERROR_C_FUNCTION_LAYOUT_CHECK_RETURN_TYPE, FuncName):\r
continue\r
- Index = Result[0].find(ReturnType)\r
+ Result0 = Result[0]\r
+ if Result0.upper().startswith('STATIC'):\r
+ Result0 = Result0[6:].strip()\r
+ Index = Result0.find(ReturnType)\r
if Index != 0 or Result[3] != 0:\r
PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_RETURN_TYPE, '[%s] Return Type should appear at the start of line' % FuncName, 'Function', Result[1])\r
\r
- if Result[2] == Result[4]:\r
- PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_RETURN_TYPE, '[%s] Return Type should appear on its own line' % FuncName, 'Function', Result[1])\r
-\r
def CheckFuncLayoutModifier(FullFileName):\r
ErrorMsgList = []\r
\r
for Result in ResultSet:\r
ReturnType = GetDataTypeFromModifier(Result[0])\r
TypeStart = ReturnType.split()[0]\r
-# if len(ReturnType) == 0:\r
-# continue\r
- Index = Result[0].find(TypeStart)\r
+ Result0 = Result[0]\r
+ if Result0.upper().startswith('STATIC'):\r
+ Result0 = Result0[6:].strip()\r
+ Index = Result0.find(TypeStart)\r
if Index != 0:\r
PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_OPTIONAL_FUNCTIONAL_MODIFIER, '', FileTable, Result[1])\r
\r
for Result in ResultSet:\r
ReturnType = GetDataTypeFromModifier(Result[0])\r
TypeStart = ReturnType.split()[0]\r
-# if len(ReturnType) == 0:\r
-# continue\r
- Index = Result[0].find(TypeStart)\r
+ Result0 = Result[0]\r
+ if Result0.upper().startswith('STATIC'):\r
+ Result0 = Result0[6:].strip()\r
+ Index = Result0.find(TypeStart)\r
if Index != 0:\r
PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_OPTIONAL_FUNCTIONAL_MODIFIER, '', 'Function', Result[1])\r
\r
FL.append(Result)\r
\r
for F in FL:\r
- SqlStatement = """ select Name, Value, ID\r
+ SqlStatement = """ select Name, Value, ID, Modifier\r
from %s\r
where Model = %d and BelongsToFunction = %d\r
""" % (FileTable, DataClass.MODEL_IDENTIFIER_VARIABLE, F[0])\r
continue\r
\r
for Result in ResultSet:\r
- if len(Result[1]) > 0:\r
+ if len(Result[1]) > 0 and 'CONST' not in Result[3]:\r
PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_NO_INIT_OF_VARIABLE, 'Variable Name: %s' % Result[0], FileTable, Result[2])\r
\r
def CheckMemberVariableFormat(Name, Value, FileTable, TdId, ModelId):\r
Fields = Value[LBPos + 1 : RBPos]\r
Fields = StripComments(Fields).strip()\r
NestPos = Fields.find ('struct')\r
- if NestPos != -1 and (NestPos + len('struct') < len(Fields)):\r
+ if NestPos != -1 and (NestPos + len('struct') < len(Fields)) and ModelId != DataClass.MODEL_IDENTIFIER_UNION:\r
if not Fields[NestPos + len('struct') + 1].isalnum():\r
if not EccGlobalData.gException.IsException(ERROR_DECLARATION_DATA_TYPE_CHECK_NESTED_STRUCTURE, Name):\r
PrintErrorMsg(ERROR_DECLARATION_DATA_TYPE_CHECK_NESTED_STRUCTURE, 'Nested struct in [%s].' % (Name), FileTable, TdId)\r
Field = Field.strip()\r
if Field == '':\r
continue\r
+ if Field.startswith("#"):\r
+ continue\r
# Enum could directly assign value to variable\r
Field = Field.split('=')[0].strip()\r
TokenList = Field.split()\r
# Remove pointers before variable\r
- if not Pattern.match(TokenList[-1].lstrip('*')):\r
- ErrMsgList.append(TokenList[-1].lstrip('*'))\r
+ Token = TokenList[-1]\r
+ if Token in ['OPTIONAL']:\r
+ Token = TokenList[-2]\r
+ if not Pattern.match(Token.lstrip('*')):\r
+ ErrMsgList.append(Token.lstrip('*'))\r
\r
return ErrMsgList\r
\r
# Check member variable format.\r
ErrMsgList = CheckMemberVariableFormat(Name, Value, FileTable, Td[5], ModelId)\r
for ErrMsg in ErrMsgList:\r
- if EccGlobalData.gException.IsException(ERROR_NAMING_CONVENTION_CHECK_VARIABLE_NAME, Name+'.'+ErrMsg):\r
+ if EccGlobalData.gException.IsException(ERROR_NAMING_CONVENTION_CHECK_VARIABLE_NAME, Name + '.' + ErrMsg):\r
continue\r
- PrintErrorMsg(ERROR_NAMING_CONVENTION_CHECK_VARIABLE_NAME, 'Member variable [%s] NOT follow naming convention.' % (Name+'.'+ErrMsg), FileTable, Td[5])\r
+ PrintErrorMsg(ERROR_NAMING_CONVENTION_CHECK_VARIABLE_NAME, 'Member variable [%s] NOT follow naming convention.' % (Name + '.' + ErrMsg), FileTable, Td[5])\r
\r
# First check in current file to see whether struct/union/enum is typedef-ed.\r
UntypedefedList = []\r
continue\r
ErrMsgList = CheckMemberVariableFormat(Name, Value, FileTable, Result[3], ModelId)\r
for ErrMsg in ErrMsgList:\r
- if EccGlobalData.gException.IsException(ERROR_NAMING_CONVENTION_CHECK_VARIABLE_NAME, Result[0]+'.'+ErrMsg):\r
+ if EccGlobalData.gException.IsException(ERROR_NAMING_CONVENTION_CHECK_VARIABLE_NAME, Result[0] + '.' + ErrMsg):\r
continue\r
- PrintErrorMsg(ERROR_NAMING_CONVENTION_CHECK_VARIABLE_NAME, 'Member variable [%s] NOT follow naming convention.' % (Result[0]+'.'+ErrMsg), FileTable, Result[3])\r
+ PrintErrorMsg(ERROR_NAMING_CONVENTION_CHECK_VARIABLE_NAME, 'Member variable [%s] NOT follow naming convention.' % (Result[0] + '.' + ErrMsg), FileTable, Result[3])\r
# Check whether it is typedefed.\r
Found = False\r
for Td in TdList:\r
if SearchInCache:\r
Type = FuncReturnTypeDict.get(PredVarStr)\r
if Type != None:\r
- if Type.find('*') != -1:\r
+ if Type.find('*') != -1 and Type != 'BOOLEAN*':\r
PrintErrorMsg(ERROR_PREDICATE_EXPRESSION_CHECK_COMPARISON_NULL_TYPE, 'Predicate Expression: %s' % Exp, FileTable, Str[2])\r
continue\r
\r
if Type == None:\r
continue\r
Type = GetTypeFromArray(Type, PredVarStr)\r
- if Type.find('*') != -1:\r
+ if Type.find('*') != -1 and Type != 'BOOLEAN*':\r
PrintErrorMsg(ERROR_PREDICATE_EXPRESSION_CHECK_COMPARISON_NULL_TYPE, 'Predicate Expression: %s' % Exp, FileTable, Str[2])\r
\r
def CheckNonBooleanValueComparison(FullFileName):\r
continue\r
\r
for Exp in GetPredicateListFromPredicateExpStr(Str[0]):\r
-# if p.match(Exp):\r
-# continue\r
PredInfo = SplitPredicateStr(Exp)\r
if PredInfo[1] == None:\r
PredVarStr = PredInfo[0][0].strip()\r
\r
if PredVarStr in FuncReturnTypeDict:\r
continue\r
-\r
Type = GetVarInfo(PredVarList, FuncRecord, FullFileName, IsFuncCall, 'BOOLEAN', StarList)\r
if SearchInCache:\r
FuncReturnTypeDict[PredVarStr] = Type\r
where Model = %d or Model = %d\r
""" % (FileTable, DataClass.MODEL_IDENTIFIER_COMMENT, DataClass.MODEL_IDENTIFIER_FUNCTION_HEADER)\r
ResultSet = Db.TblFile.Exec(SqlStatement)\r
- DoxygenCommandList = ['bug', 'todo', 'example', 'file', 'attention', 'param', 'post', 'pre', 'retval', 'return', 'sa', 'since', 'test', 'note', 'par']\r
+ DoxygenCommandList = ['bug', 'todo', 'example', 'file', 'attention', 'param', 'post', 'pre', 'retval',\r
+ 'return', 'sa', 'since', 'test', 'note', 'par', 'endcode', 'code']\r
for Result in ResultSet:\r
CommentStr = Result[0]\r
CommentPartList = CommentStr.split()\r
if Part.startswith('@'):\r
if EccGlobalData.gException.IsException(ERROR_DOXYGEN_CHECK_COMMAND, Part):\r
continue\r
+ if not Part.replace('@', '').strip():\r
+ continue\r
+ if Part.lstrip('@') in ['{', '}']:\r
+ continue\r
if Part.lstrip('@').isalpha():\r
if Part.lstrip('@') not in DoxygenCommandList:\r
PrintErrorMsg(ERROR_DOXYGEN_CHECK_COMMAND, 'Unknown doxygen command %s' % Part, FileTable, Result[1])\r
FileTable = 'Identifier' + str(FileID)\r
SqlStatement = """ select Value, ID\r
from %s\r
- where Model = %d and StartLine = 1 and StartColumn = 0\r
+ where Model = %d and (StartLine = 1 or StartLine = 7 or StartLine = 8) and StartColumn = 0\r
""" % (FileTable, DataClass.MODEL_IDENTIFIER_COMMENT)\r
ResultSet = Db.TblFile.Exec(SqlStatement)\r
if len(ResultSet) == 0:\r
- PrintErrorMsg(ERROR_HEADER_CHECK_FILE, 'No Comment appear at the very beginning of file.', 'File', FileID)\r
+ PrintErrorMsg(ERROR_HEADER_CHECK_FILE, 'No File License header appear at the very beginning of file.', 'File', FileID)\r
return ErrorMsgList\r
\r
+ NoHeaderCommentStartFlag = True\r
+ NoHeaderCommentEndFlag = True\r
+ NoHeaderCommentPeriodFlag = True\r
+ NoCopyrightFlag = True\r
+ NoLicenseFlag = True\r
+ NoRevReferFlag = True\r
+ NextLineIndex = 0\r
for Result in ResultSet:\r
- CommentStr = Result[0]\r
- if not CommentStr.startswith('/** @file'):\r
- PrintErrorMsg(ERROR_DOXYGEN_CHECK_FILE_HEADER, 'File header comment should begin with ""/** @file""', FileTable, Result[1])\r
- if not CommentStr.endswith('**/'):\r
- PrintErrorMsg(ERROR_HEADER_CHECK_FILE, 'File header comment should end with **/', FileTable, Result[1])\r
- if CommentStr.find('.') == -1:\r
- PrintErrorMsg(ERROR_DOXYGEN_CHECK_COMMENT_DESCRIPTION, 'Comment description should end with period \'.\'', FileTable, Result[1])\r
+ FileStartFlag = False\r
+ CommentStrList = []\r
+ CommentStr = Result[0].strip()\r
+ CommentStrListTemp = CommentStr.split('\n')\r
+ if (len(CommentStrListTemp) <= 1):\r
+ # For Mac\r
+ CommentStrListTemp = CommentStr.split('\r')\r
+ # Skip the content before the file header \r
+ for CommentLine in CommentStrListTemp:\r
+ if CommentLine.strip().startswith('/** @file'):\r
+ FileStartFlag = True\r
+ if FileStartFlag == True:\r
+ CommentStrList.append(CommentLine)\r
+ \r
+ ID = Result[1]\r
+ Index = 0\r
+ if CommentStrList and CommentStrList[0].strip().startswith('/** @file'):\r
+ NoHeaderCommentStartFlag = False\r
+ else:\r
+ continue\r
+ if CommentStrList and CommentStrList[-1].strip().endswith('**/'):\r
+ NoHeaderCommentEndFlag = False\r
+ else:\r
+ continue\r
+\r
+ for CommentLine in CommentStrList:\r
+ Index = Index + 1\r
+ NextLineIndex = Index\r
+ if CommentLine.startswith('/** @file'):\r
+ continue\r
+ if CommentLine.startswith('**/'):\r
+ break\r
+ # Check whether C File header Comment content start with two spaces.\r
+ if EccGlobalData.gConfig.HeaderCheckCFileCommentStartSpacesNum == '1' or EccGlobalData.gConfig.HeaderCheckAll == '1' or EccGlobalData.gConfig.CheckAll == '1':\r
+ if CommentLine.startswith('/** @file') == False and CommentLine.startswith('**/') == False and CommentLine.strip() and CommentLine.startswith(' ') == False:\r
+ PrintErrorMsg(ERROR_HEADER_CHECK_FILE, 'File header comment content should start with two spaces at each line', FileTable, ID)\r
+ \r
+ CommentLine = CommentLine.strip()\r
+ if CommentLine.startswith('Copyright'):\r
+ NoCopyrightFlag = False\r
+ if CommentLine.find('All rights reserved') == -1:\r
+ for Copyright in EccGlobalData.gConfig.Copyright:\r
+ if CommentLine.find(Copyright) > -1:\r
+ PrintErrorMsg(ERROR_HEADER_CHECK_FILE, '""All rights reserved"" announcement should be following the ""Copyright"" at the same line', FileTable, ID)\r
+ break\r
+ if CommentLine.endswith('<BR>') == -1:\r
+ PrintErrorMsg(ERROR_HEADER_CHECK_FILE, 'The ""<BR>"" at the end of the Copyright line is required', FileTable, ID)\r
+ if NextLineIndex < len(CommentStrList) and CommentStrList[NextLineIndex].strip().startswith('Copyright') == False and CommentStrList[NextLineIndex].strip():\r
+ NoLicenseFlag = False\r
+ if CommentLine.startswith('@par Revision Reference:'):\r
+ NoRevReferFlag = False\r
+ RefListFlag = False\r
+ for RefLine in CommentStrList[NextLineIndex:]:\r
+ if RefLine.strip() and (NextLineIndex + 1) < len(CommentStrList) and CommentStrList[NextLineIndex+1].strip() and CommentStrList[NextLineIndex+1].strip().startswith('**/') == False:\r
+ RefListFlag = True\r
+ if RefLine.strip() == False or RefLine.strip().startswith('**/'):\r
+ RefListFlag = False\r
+ break\r
+ # Check whether C File header Comment's each reference at list should begin with a bullet character.\r
+ if EccGlobalData.gConfig.HeaderCheckCFileCommentReferenceFormat == '1' or EccGlobalData.gConfig.HeaderCheckAll == '1' or EccGlobalData.gConfig.CheckAll == '1':\r
+ if RefListFlag == True:\r
+ if RefLine.strip() and RefLine.strip().startswith('**/') == False and RefLine.startswith(' -') == False: \r
+ PrintErrorMsg(ERROR_HEADER_CHECK_FILE, 'Each reference on a separate line should begin with a bullet character ""-"" ', FileTable, ID) \r
+ \r
+ if NoHeaderCommentStartFlag:\r
+ PrintErrorMsg(ERROR_DOXYGEN_CHECK_FILE_HEADER, 'File header comment should begin with ""/** @file""', FileTable, ID)\r
+ return\r
+ if NoHeaderCommentEndFlag:\r
+ PrintErrorMsg(ERROR_HEADER_CHECK_FILE, 'File header comment should end with ""**/""', FileTable, ID)\r
+ return\r
+ if NoCopyrightFlag:\r
+ PrintErrorMsg(ERROR_HEADER_CHECK_FILE, 'File header comment missing the ""Copyright""', FileTable, ID)\r
+ #Check whether C File header Comment have the License immediately after the ""Copyright"" line.\r
+ if EccGlobalData.gConfig.HeaderCheckCFileCommentLicenseFormat == '1' or EccGlobalData.gConfig.HeaderCheckAll == '1' or EccGlobalData.gConfig.CheckAll == '1':\r
+ if NoLicenseFlag:\r
+ PrintErrorMsg(ERROR_HEADER_CHECK_FILE, 'File header comment should have the License immediately after the ""Copyright"" line', FileTable, ID)\r
\r
def CheckFuncHeaderDoxygenComments(FullFileName):\r
ErrorMsgList = []\r
\r
return DoxygenStrList\r
\r
-def CheckGeneralDoxygenCommentLayout(Str, StartLine, ErrorMsgList, CommentId = -1, TableName = ''):\r
+def CheckGeneralDoxygenCommentLayout(Str, StartLine, ErrorMsgList, CommentId= -1, TableName=''):\r
#/** --*/ @retval after @param\r
if not Str.startswith('/**'):\r
ErrorMsgList.append('Line %d : Comment does NOT have prefix /** ' % StartLine)\r
ErrorMsgList.append('Line %d : @retval appear before @param ' % StartLine)\r
PrintErrorMsg(ERROR_DOXYGEN_CHECK_FUNCTION_HEADER, 'in Comment, @retval appear before @param ', TableName, CommentId)\r
\r
-def CheckFunctionHeaderConsistentWithDoxygenComment(FuncModifier, FuncHeader, FuncStartLine, CommentStr, CommentStartLine, ErrorMsgList, CommentId = -1, TableName = ''):\r
+def CheckFunctionHeaderConsistentWithDoxygenComment(FuncModifier, FuncHeader, FuncStartLine, CommentStr, CommentStartLine, ErrorMsgList, CommentId= -1, TableName=''):\r
\r
ParamList = GetParamList(FuncHeader)\r
CheckGeneralDoxygenCommentLayout(CommentStr, CommentStartLine, ErrorMsgList, CommentId, TableName)\r
ParamName = ParamList[Index].Name.strip()\r
Tag = DoxygenStrList[Index].strip(' ')\r
if (not Tag[-1] == ('\n')) and (not Tag[-1] == ('\r')):\r
- ErrorMsgList.append('Line %d : in Comment, \"%s\" does NOT end with new line ' % (CommentStartLine, Tag.replace('\n', '').replace('\r', '')))\r
- PrintErrorMsg(ERROR_HEADER_CHECK_FUNCTION, 'in Comment, \"%s\" does NOT end with new line ' % (Tag.replace('\n', '').replace('\r', '')), TableName, CommentId)\r
+ ErrorMsgList.append('Line %d : in Comment, <%s> does NOT end with new line ' % (CommentStartLine, Tag.replace('\n', '').replace('\r', '')))\r
+ PrintErrorMsg(ERROR_HEADER_CHECK_FUNCTION, 'in Comment, <%s> does NOT end with new line ' % (Tag.replace('\n', '').replace('\r', '')), TableName, CommentId)\r
TagPartList = Tag.split()\r
if len(TagPartList) < 2:\r
- ErrorMsgList.append('Line %d : in Comment, \"%s\" does NOT contain doxygen contents ' % (CommentStartLine, Tag.replace('\n', '').replace('\r', '')))\r
- PrintErrorMsg(ERROR_DOXYGEN_CHECK_FUNCTION_HEADER, 'in Comment, \"%s\" does NOT contain doxygen contents ' % (Tag.replace('\n', '').replace('\r', '')), TableName, CommentId)\r
+ ErrorMsgList.append('Line %d : in Comment, <%s> does NOT contain doxygen contents ' % (CommentStartLine, Tag.replace('\n', '').replace('\r', '')))\r
+ PrintErrorMsg(ERROR_DOXYGEN_CHECK_FUNCTION_HEADER, 'in Comment, <%s> does NOT contain doxygen contents ' % (Tag.replace('\n', '').replace('\r', '')), TableName, CommentId)\r
Index += 1\r
continue\r
LBPos = Tag.find('[')\r
RBPos = Tag.find(']')\r
ParamToLBContent = Tag[len('@param'):LBPos].strip()\r
- if LBPos > 0 and len(ParamToLBContent)==0 and RBPos > LBPos:\r
+ if LBPos > 0 and len(ParamToLBContent) == 0 and RBPos > LBPos:\r
InOutStr = ''\r
ModifierPartList = ParamModifier.split()\r
for Part in ModifierPartList:\r
InOutStr = 'out'\r
\r
if InOutStr != '':\r
- if Tag.find('['+InOutStr+']') == -1:\r
- ErrorMsgList.append('Line %d : in Comment, \"%s\" does NOT have %s ' % (CommentStartLine, (TagPartList[0] + ' ' +TagPartList[1]).replace('\n', '').replace('\r', ''), '['+InOutStr+']'))\r
- PrintErrorMsg(ERROR_DOXYGEN_CHECK_FUNCTION_HEADER, 'in Comment, \"%s\" does NOT have %s ' % ((TagPartList[0] + ' ' +TagPartList[1]).replace('\n', '').replace('\r', ''), '['+InOutStr+']'), TableName, CommentId)\r
+ if Tag.find('[' + InOutStr + ']') == -1:\r
+ if InOutStr != 'in, out':\r
+ ErrorMsgList.append('Line %d : in Comment, <%s> does NOT have %s ' % (CommentStartLine, (TagPartList[0] + ' ' + TagPartList[1]).replace('\n', '').replace('\r', ''), '[' + InOutStr + ']'))\r
+ PrintErrorMsg(ERROR_DOXYGEN_CHECK_FUNCTION_HEADER, 'in Comment, <%s> does NOT have %s ' % ((TagPartList[0] + ' ' + TagPartList[1]).replace('\n', '').replace('\r', ''), '[' + InOutStr + ']'), TableName, CommentId)\r
+ else:\r
+ if Tag.find('[in,out]') == -1:\r
+ ErrorMsgList.append('Line %d : in Comment, <%s> does NOT have %s ' % (CommentStartLine, (TagPartList[0] + ' ' + TagPartList[1]).replace('\n', '').replace('\r', ''), '[' + InOutStr + ']'))\r
+ PrintErrorMsg(ERROR_DOXYGEN_CHECK_FUNCTION_HEADER, 'in Comment, <%s> does NOT have %s ' % ((TagPartList[0] + ' ' + TagPartList[1]).replace('\n', '').replace('\r', ''), '[' + InOutStr + ']'), TableName, CommentId)\r
+\r
+\r
if Tag.find(ParamName) == -1 and ParamName != 'VOID' and ParamName != 'void':\r
- ErrorMsgList.append('Line %d : in Comment, \"%s\" does NOT consistent with parameter name %s ' % (CommentStartLine, (TagPartList[0] + ' ' +TagPartList[1]).replace('\n', '').replace('\r', ''), ParamName))\r
- PrintErrorMsg(ERROR_DOXYGEN_CHECK_FUNCTION_HEADER, 'in Comment, \"%s\" does NOT consistent with parameter name %s ' % ((TagPartList[0] + ' ' +TagPartList[1]).replace('\n', '').replace('\r', ''), ParamName), TableName, CommentId)\r
+ ErrorMsgList.append('Line %d : in Comment, <%s> does NOT consistent with parameter name %s ' % (CommentStartLine, (TagPartList[0] + ' ' + TagPartList[1]).replace('\n', '').replace('\r', ''), ParamName))\r
+ PrintErrorMsg(ERROR_DOXYGEN_CHECK_FUNCTION_HEADER, 'in Comment, <%s> does NOT consistent with parameter name %s ' % ((TagPartList[0] + ' ' + TagPartList[1]).replace('\n', '').replace('\r', ''), ParamName), TableName, CommentId)\r
Index += 1\r
\r
if Index < ParamNumber:\r
# EdkLogger.Initialize()\r
# EdkLogger.SetLevel(EdkLogger.QUIET)\r
# CollectSourceCodeDataIntoDB(sys.argv[1])\r
- MsgList = CheckFuncHeaderDoxygenComments('C:\\Combo\\R9\\LakeportX64Dev\\FlashDevicePkg\\Library\\SpiFlashChipM25P64\\SpiFlashChipM25P64.c')\r
+ try:\r
+ test_file = sys.argv[1]\r
+ except IndexError, v:\r
+ print "Usage: %s filename" % sys.argv[0]\r
+ sys.exit(1)\r
+ MsgList = CheckFuncHeaderDoxygenComments(test_file)\r
for Msg in MsgList:\r
print Msg\r
print 'Done!'\r