]> git.proxmox.com Git - mirror_edk2.git/blame - BaseTools/Source/Python/Ecc/c.py
BaseTools: Replace StandardError with Expression
[mirror_edk2.git] / BaseTools / Source / Python / Ecc / c.py
CommitLineData
52302d4d
LG
1## @file\r
2# This file is used to be the c coding style checking of ECC tool\r
3#\r
dbc85eb9 4# Copyright (c) 2009 - 2018, Intel Corporation. All rights reserved.<BR>\r
40d841f6 5# This program and the accompanying materials\r
52302d4d
LG
6# are licensed and made available under the terms and conditions of the BSD License\r
7# which accompanies this distribution. The full text of the license may be found at\r
8# http://opensource.org/licenses/bsd-license.php\r
9#\r
10# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
11# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
12#\r
13\r
72443dd2 14from __future__ import print_function\r
30fdf114 15import sys\r
1be2ed90 16import Common.LongFilePathOs as os\r
30fdf114
LG
17import re\r
18import string\r
19import CodeFragmentCollector\r
20import FileProfile\r
21from CommonDataClass import DataClass\r
22import Database\r
23from Common import EdkLogger\r
24from EccToolError import *\r
25import EccGlobalData\r
26import MetaDataParser\r
27\r
28IncludeFileListDict = {}\r
29AllIncludeFileListDict = {}\r
30IncludePathListDict = {}\r
31ComplexTypeDict = {}\r
32SUDict = {}\r
33IgnoredKeywordList = ['EFI_ERROR']\r
34\r
35def GetIgnoredDirListPattern():\r
36 skipList = list(EccGlobalData.gConfig.SkipDirList) + ['.svn']\r
37 DirString = string.join(skipList, '|')\r
38 p = re.compile(r'.*[\\/](?:%s)[\\/]?.*' % DirString)\r
39 return p\r
40\r
41def GetFuncDeclPattern():\r
42 p = re.compile(r'(?:EFIAPI|EFI_BOOT_SERVICE|EFI_RUNTIME_SERVICE)?\s*[_\w]+\s*\(.*\)$', re.DOTALL)\r
43 return p\r
44\r
45def GetArrayPattern():\r
46 p = re.compile(r'[_\w]*\s*[\[.*\]]+')\r
47 return p\r
48\r
49def GetTypedefFuncPointerPattern():\r
50 p = re.compile('[_\w\s]*\([\w\s]*\*+\s*[_\w]+\s*\)\s*\(.*\)', re.DOTALL)\r
51 return p\r
52\r
53def GetDB():\r
54 return EccGlobalData.gDb\r
55\r
56def GetConfig():\r
57 return EccGlobalData.gConfig\r
58\r
59def PrintErrorMsg(ErrorType, Msg, TableName, ItemId):\r
60 Msg = Msg.replace('\n', '').replace('\r', '')\r
61 MsgPartList = Msg.split()\r
62 Msg = ''\r
63 for Part in MsgPartList:\r
64 Msg += Part\r
65 Msg += ' '\r
79b74a03 66 GetDB().TblReport.Insert(ErrorType, OtherMsg=Msg, BelongsToTable=TableName, BelongsToItem=ItemId)\r
30fdf114
LG
67\r
68def GetIdType(Str):\r
69 Type = DataClass.MODEL_UNKNOWN\r
70 Str = Str.replace('#', '# ')\r
71 List = Str.split()\r
72 if List[1] == 'include':\r
73 Type = DataClass.MODEL_IDENTIFIER_INCLUDE\r
74 elif List[1] == 'define':\r
75 Type = DataClass.MODEL_IDENTIFIER_MACRO_DEFINE\r
76 elif List[1] == 'ifdef':\r
77 Type = DataClass.MODEL_IDENTIFIER_MACRO_IFDEF\r
78 elif List[1] == 'ifndef':\r
79 Type = DataClass.MODEL_IDENTIFIER_MACRO_IFNDEF\r
80 elif List[1] == 'endif':\r
81 Type = DataClass.MODEL_IDENTIFIER_MACRO_ENDIF\r
82 elif List[1] == 'pragma':\r
83 Type = DataClass.MODEL_IDENTIFIER_MACRO_PROGMA\r
84 else:\r
85 Type = DataClass.MODEL_UNKNOWN\r
86 return Type\r
87\r
88def SuOccurInTypedef (Su, TdList):\r
89 for Td in TdList:\r
90 if Su.StartPos[0] == Td.StartPos[0] and Su.EndPos[0] == Td.EndPos[0]:\r
91 return True\r
92 return False\r
93\r
94def GetIdentifierList():\r
95 IdList = []\r
96 for comment in FileProfile.CommentList:\r
79b74a03 97 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
30fdf114 98 IdList.append(IdComment)\r
52302d4d 99\r
30fdf114
LG
100 for pp in FileProfile.PPDirectiveList:\r
101 Type = GetIdType(pp.Content)\r
79b74a03 102 IdPP = DataClass.IdentifierClass(-1, '', '', '', pp.Content, Type, -1, -1, pp.StartPos[0], pp.StartPos[1], pp.EndPos[0], pp.EndPos[1])\r
30fdf114 103 IdList.append(IdPP)\r
52302d4d 104\r
30fdf114 105 for pe in FileProfile.PredicateExpressionList:\r
79b74a03 106 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
30fdf114 107 IdList.append(IdPE)\r
52302d4d 108\r
30fdf114
LG
109 FuncDeclPattern = GetFuncDeclPattern()\r
110 ArrayPattern = GetArrayPattern()\r
111 for var in FileProfile.VariableDeclarationList:\r
112 DeclText = var.Declarator.lstrip()\r
113 FuncPointerPattern = GetTypedefFuncPointerPattern()\r
114 if FuncPointerPattern.match(DeclText):\r
115 continue\r
116 VarNameStartLine = var.NameStartPos[0]\r
117 VarNameStartColumn = var.NameStartPos[1]\r
118 FirstChar = DeclText[0]\r
119 while not FirstChar.isalpha() and FirstChar != '_':\r
120 if FirstChar == '*':\r
121 var.Modifier += '*'\r
122 VarNameStartColumn += 1\r
123 DeclText = DeclText.lstrip('*')\r
124 elif FirstChar == '\r':\r
125 DeclText = DeclText.lstrip('\r\n').lstrip('\r')\r
126 VarNameStartLine += 1\r
127 VarNameStartColumn = 0\r
128 elif FirstChar == '\n':\r
129 DeclText = DeclText.lstrip('\n')\r
130 VarNameStartLine += 1\r
131 VarNameStartColumn = 0\r
132 elif FirstChar == ' ':\r
133 DeclText = DeclText.lstrip(' ')\r
134 VarNameStartColumn += 1\r
135 elif FirstChar == '\t':\r
136 DeclText = DeclText.lstrip('\t')\r
137 VarNameStartColumn += 8\r
138 else:\r
139 DeclText = DeclText[1:]\r
140 VarNameStartColumn += 1\r
141 FirstChar = DeclText[0]\r
52302d4d 142\r
30fdf114
LG
143 var.Declarator = DeclText\r
144 if FuncDeclPattern.match(var.Declarator):\r
52302d4d 145 DeclSplitList = var.Declarator.split('(')\r
30fdf114
LG
146 FuncName = DeclSplitList[0].strip()\r
147 FuncNamePartList = FuncName.split()\r
148 if len(FuncNamePartList) > 1:\r
149 FuncName = FuncNamePartList[-1].strip()\r
150 NameStart = DeclSplitList[0].rfind(FuncName)\r
151 var.Declarator = var.Declarator[NameStart:]\r
152 if NameStart > 0:\r
153 var.Modifier += ' ' + DeclSplitList[0][0:NameStart]\r
154 Index = 0\r
155 PreChar = ''\r
156 while Index < NameStart:\r
157 FirstChar = DeclSplitList[0][Index]\r
158 if DeclSplitList[0][Index:].startswith('EFIAPI'):\r
159 Index += 6\r
160 VarNameStartColumn += 6\r
161 PreChar = ''\r
162 continue\r
163 elif FirstChar == '\r':\r
164 Index += 1\r
165 VarNameStartLine += 1\r
166 VarNameStartColumn = 0\r
167 elif FirstChar == '\n':\r
168 Index += 1\r
169 if PreChar != '\r':\r
170 VarNameStartLine += 1\r
171 VarNameStartColumn = 0\r
172 elif FirstChar == ' ':\r
173 Index += 1\r
174 VarNameStartColumn += 1\r
175 elif FirstChar == '\t':\r
176 Index += 1\r
177 VarNameStartColumn += 8\r
178 else:\r
179 Index += 1\r
180 VarNameStartColumn += 1\r
181 PreChar = FirstChar\r
182 IdVar = DataClass.IdentifierClass(-1, var.Modifier, '', var.Declarator, FuncName, DataClass.MODEL_IDENTIFIER_FUNCTION_DECLARATION, -1, -1, var.StartPos[0], var.StartPos[1], VarNameStartLine, VarNameStartColumn)\r
183 IdList.append(IdVar)\r
184 continue\r
52302d4d
LG
185\r
186 if var.Declarator.find('{') == -1:\r
30fdf114
LG
187 for decl in var.Declarator.split(','):\r
188 DeclList = decl.split('=')\r
189 Name = DeclList[0].strip()\r
190 if ArrayPattern.match(Name):\r
191 LSBPos = var.Declarator.find('[')\r
192 var.Modifier += ' ' + Name[LSBPos:]\r
193 Name = Name[0:LSBPos]\r
52302d4d 194\r
79b74a03 195 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
30fdf114
LG
196 IdList.append(IdVar)\r
197 else:\r
198 DeclList = var.Declarator.split('=')\r
199 Name = DeclList[0].strip()\r
200 if ArrayPattern.match(Name):\r
201 LSBPos = var.Declarator.find('[')\r
202 var.Modifier += ' ' + Name[LSBPos:]\r
203 Name = Name[0:LSBPos]\r
79b74a03 204 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
30fdf114 205 IdList.append(IdVar)\r
52302d4d 206\r
30fdf114
LG
207 for enum in FileProfile.EnumerationDefinitionList:\r
208 LBPos = enum.Content.find('{')\r
209 RBPos = enum.Content.find('}')\r
210 Name = enum.Content[4:LBPos].strip()\r
79b74a03
LG
211 Value = enum.Content[LBPos + 1:RBPos]\r
212 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
30fdf114 213 IdList.append(IdEnum)\r
52302d4d 214\r
30fdf114
LG
215 for su in FileProfile.StructUnionDefinitionList:\r
216 if SuOccurInTypedef(su, FileProfile.TypedefDefinitionList):\r
217 continue\r
218 Type = DataClass.MODEL_IDENTIFIER_STRUCTURE\r
219 SkipLen = 6\r
220 if su.Content.startswith('union'):\r
221 Type = DataClass.MODEL_IDENTIFIER_UNION\r
222 SkipLen = 5\r
223 LBPos = su.Content.find('{')\r
224 RBPos = su.Content.find('}')\r
225 if LBPos == -1 or RBPos == -1:\r
226 Name = su.Content[SkipLen:].strip()\r
227 Value = ''\r
228 else:\r
229 Name = su.Content[SkipLen:LBPos].strip()\r
79b74a03
LG
230 Value = su.Content[LBPos:RBPos + 1]\r
231 IdPE = DataClass.IdentifierClass(-1, '', '', Name, Value, Type, -1, -1, su.StartPos[0], su.StartPos[1], su.EndPos[0], su.EndPos[1])\r
30fdf114 232 IdList.append(IdPE)\r
52302d4d
LG
233\r
234 TdFuncPointerPattern = GetTypedefFuncPointerPattern()\r
30fdf114
LG
235 for td in FileProfile.TypedefDefinitionList:\r
236 Modifier = ''\r
237 Name = td.ToType\r
238 Value = td.FromType\r
239 if TdFuncPointerPattern.match(td.ToType):\r
240 Modifier = td.FromType\r
241 LBPos = td.ToType.find('(')\r
79b74a03 242 TmpStr = td.ToType[LBPos + 1:].strip()\r
30fdf114
LG
243 StarPos = TmpStr.find('*')\r
244 if StarPos != -1:\r
245 Modifier += ' ' + TmpStr[0:StarPos]\r
246 while TmpStr[StarPos] == '*':\r
247# Modifier += ' ' + '*'\r
248 StarPos += 1\r
249 TmpStr = TmpStr[StarPos:].strip()\r
250 RBPos = TmpStr.find(')')\r
251 Name = TmpStr[0:RBPos]\r
252 Value = 'FP' + TmpStr[RBPos + 1:]\r
253 else:\r
254 while Name.startswith('*'):\r
255 Value += ' ' + '*'\r
256 Name = Name.lstrip('*').strip()\r
52302d4d 257\r
30fdf114
LG
258 if Name.find('[') != -1:\r
259 LBPos = Name.find('[')\r
260 RBPos = Name.rfind(']')\r
261 Value += Name[LBPos : RBPos + 1]\r
262 Name = Name[0 : LBPos]\r
52302d4d 263\r
79b74a03 264 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
30fdf114 265 IdList.append(IdTd)\r
52302d4d 266\r
30fdf114 267 for funcCall in FileProfile.FunctionCallingList:\r
79b74a03 268 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
30fdf114
LG
269 IdList.append(IdFC)\r
270 return IdList\r
271\r
272def StripNonAlnumChars(Str):\r
273 StrippedStr = ''\r
274 for Char in Str:\r
b7f63a5a 275 if Char.isalnum() or Char == '_':\r
30fdf114
LG
276 StrippedStr += Char\r
277 return StrippedStr\r
278\r
79b74a03 279def GetParamList(FuncDeclarator, FuncNameLine=0, FuncNameOffset=0):\r
30fdf114
LG
280 FuncDeclarator = StripComments(FuncDeclarator)\r
281 ParamIdList = []\r
282 #DeclSplitList = FuncDeclarator.split('(')\r
283 LBPos = FuncDeclarator.find('(')\r
284 #if len(DeclSplitList) < 2:\r
285 if LBPos == -1:\r
286 return ParamIdList\r
287 #FuncName = DeclSplitList[0]\r
288 FuncName = FuncDeclarator[0:LBPos]\r
289 #ParamStr = DeclSplitList[1].rstrip(')')\r
290 ParamStr = FuncDeclarator[LBPos + 1:].rstrip(')')\r
291 LineSkipped = 0\r
292 OffsetSkipped = 0\r
293 TailChar = FuncName[-1]\r
294 while not TailChar.isalpha() and TailChar != '_':\r
52302d4d 295\r
30fdf114
LG
296 if TailChar == '\n':\r
297 FuncName = FuncName.rstrip('\r\n').rstrip('\n')\r
298 LineSkipped += 1\r
299 OffsetSkipped = 0\r
300 elif TailChar == '\r':\r
301 FuncName = FuncName.rstrip('\r')\r
302 LineSkipped += 1\r
303 OffsetSkipped = 0\r
304 elif TailChar == ' ':\r
305 FuncName = FuncName.rstrip(' ')\r
306 OffsetSkipped += 1\r
307 elif TailChar == '\t':\r
308 FuncName = FuncName.rstrip('\t')\r
309 OffsetSkipped += 8\r
310 else:\r
311 FuncName = FuncName[:-1]\r
312 TailChar = FuncName[-1]\r
52302d4d 313\r
30fdf114 314 OffsetSkipped += 1 #skip '('\r
52302d4d 315\r
30fdf114
LG
316 for p in ParamStr.split(','):\r
317 ListP = p.split()\r
318 if len(ListP) == 0:\r
319 continue\r
320 ParamName = ListP[-1]\r
321 DeclText = ParamName.strip()\r
322 RightSpacePos = p.rfind(ParamName)\r
323 ParamModifier = p[0:RightSpacePos]\r
324 if ParamName == 'OPTIONAL':\r
325 if ParamModifier == '':\r
326 ParamModifier += ' ' + 'OPTIONAL'\r
327 DeclText = ''\r
328 else:\r
329 ParamName = ListP[-2]\r
330 DeclText = ParamName.strip()\r
331 RightSpacePos = p.rfind(ParamName)\r
332 ParamModifier = p[0:RightSpacePos]\r
333 ParamModifier += 'OPTIONAL'\r
334 while DeclText.startswith('*'):\r
335 ParamModifier += ' ' + '*'\r
336 DeclText = DeclText.lstrip('*').strip()\r
337 ParamName = DeclText\r
338 # ignore array length if exists.\r
339 LBIndex = ParamName.find('[')\r
340 if LBIndex != -1:\r
341 ParamName = ParamName[0:LBIndex]\r
52302d4d 342\r
30fdf114
LG
343 Start = RightSpacePos\r
344 Index = 0\r
345 PreChar = ''\r
346 while Index < Start:\r
347 FirstChar = p[Index]\r
52302d4d 348\r
30fdf114
LG
349 if FirstChar == '\r':\r
350 Index += 1\r
351 LineSkipped += 1\r
352 OffsetSkipped = 0\r
353 elif FirstChar == '\n':\r
354 Index += 1\r
355 if PreChar != '\r':\r
356 LineSkipped += 1\r
357 OffsetSkipped = 0\r
358 elif FirstChar == ' ':\r
359 Index += 1\r
360 OffsetSkipped += 1\r
361 elif FirstChar == '\t':\r
362 Index += 1\r
363 OffsetSkipped += 8\r
364 else:\r
365 Index += 1\r
366 OffsetSkipped += 1\r
367 PreChar = FirstChar\r
52302d4d 368\r
30fdf114
LG
369 ParamBeginLine = FuncNameLine + LineSkipped\r
370 ParamBeginOffset = FuncNameOffset + OffsetSkipped\r
52302d4d 371\r
30fdf114
LG
372 Index = Start + len(ParamName)\r
373 PreChar = ''\r
374 while Index < len(p):\r
375 FirstChar = p[Index]\r
52302d4d 376\r
30fdf114
LG
377 if FirstChar == '\r':\r
378 Index += 1\r
379 LineSkipped += 1\r
380 OffsetSkipped = 0\r
381 elif FirstChar == '\n':\r
382 Index += 1\r
383 if PreChar != '\r':\r
384 LineSkipped += 1\r
385 OffsetSkipped = 0\r
386 elif FirstChar == ' ':\r
387 Index += 1\r
388 OffsetSkipped += 1\r
389 elif FirstChar == '\t':\r
390 Index += 1\r
391 OffsetSkipped += 8\r
392 else:\r
393 Index += 1\r
394 OffsetSkipped += 1\r
395 PreChar = FirstChar\r
52302d4d 396\r
30fdf114
LG
397 ParamEndLine = FuncNameLine + LineSkipped\r
398 ParamEndOffset = FuncNameOffset + OffsetSkipped\r
399 if ParamName != '...':\r
400 ParamName = StripNonAlnumChars(ParamName)\r
401 IdParam = DataClass.IdentifierClass(-1, ParamModifier, '', ParamName, '', DataClass.MODEL_IDENTIFIER_PARAMETER, -1, -1, ParamBeginLine, ParamBeginOffset, ParamEndLine, ParamEndOffset)\r
402 ParamIdList.append(IdParam)\r
52302d4d 403\r
30fdf114 404 OffsetSkipped += 1 #skip ','\r
52302d4d 405\r
30fdf114 406 return ParamIdList\r
52302d4d 407\r
30fdf114
LG
408def GetFunctionList():\r
409 FuncObjList = []\r
410 for FuncDef in FileProfile.FunctionDefinitionList:\r
411 ParamIdList = []\r
412 DeclText = FuncDef.Declarator.lstrip()\r
413 FuncNameStartLine = FuncDef.NamePos[0]\r
414 FuncNameStartColumn = FuncDef.NamePos[1]\r
415 FirstChar = DeclText[0]\r
416 while not FirstChar.isalpha() and FirstChar != '_':\r
417 if FirstChar == '*':\r
418 FuncDef.Modifier += '*'\r
419 FuncNameStartColumn += 1\r
420 DeclText = DeclText.lstrip('*')\r
421 elif FirstChar == '\r':\r
422 DeclText = DeclText.lstrip('\r\n').lstrip('\r')\r
423 FuncNameStartLine += 1\r
424 FuncNameStartColumn = 0\r
425 elif FirstChar == '\n':\r
426 DeclText = DeclText.lstrip('\n')\r
427 FuncNameStartLine += 1\r
428 FuncNameStartColumn = 0\r
429 elif FirstChar == ' ':\r
430 DeclText = DeclText.lstrip(' ')\r
431 FuncNameStartColumn += 1\r
432 elif FirstChar == '\t':\r
433 DeclText = DeclText.lstrip('\t')\r
434 FuncNameStartColumn += 8\r
435 else:\r
436 DeclText = DeclText[1:]\r
437 FuncNameStartColumn += 1\r
438 FirstChar = DeclText[0]\r
52302d4d 439\r
30fdf114
LG
440 FuncDef.Declarator = DeclText\r
441 DeclSplitList = FuncDef.Declarator.split('(')\r
442 if len(DeclSplitList) < 2:\r
443 continue\r
52302d4d 444\r
30fdf114
LG
445 FuncName = DeclSplitList[0]\r
446 FuncNamePartList = FuncName.split()\r
447 if len(FuncNamePartList) > 1:\r
448 FuncName = FuncNamePartList[-1]\r
449 NameStart = DeclSplitList[0].rfind(FuncName)\r
450 if NameStart > 0:\r
451 FuncDef.Modifier += ' ' + DeclSplitList[0][0:NameStart]\r
452 Index = 0\r
453 PreChar = ''\r
454 while Index < NameStart:\r
455 FirstChar = DeclSplitList[0][Index]\r
456 if DeclSplitList[0][Index:].startswith('EFIAPI'):\r
457 Index += 6\r
458 FuncNameStartColumn += 6\r
459 PreChar = ''\r
460 continue\r
461 elif FirstChar == '\r':\r
462 Index += 1\r
463 FuncNameStartLine += 1\r
464 FuncNameStartColumn = 0\r
465 elif FirstChar == '\n':\r
466 Index += 1\r
467 if PreChar != '\r':\r
468 FuncNameStartLine += 1\r
469 FuncNameStartColumn = 0\r
470 elif FirstChar == ' ':\r
471 Index += 1\r
472 FuncNameStartColumn += 1\r
473 elif FirstChar == '\t':\r
474 Index += 1\r
475 FuncNameStartColumn += 8\r
476 else:\r
477 Index += 1\r
478 FuncNameStartColumn += 1\r
479 PreChar = FirstChar\r
52302d4d 480\r
79b74a03 481 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
30fdf114 482 FuncObjList.append(FuncObj)\r
52302d4d 483\r
30fdf114
LG
484 return FuncObjList\r
485\r
486def GetFileModificationTimeFromDB(FullFileName):\r
487 TimeValue = 0.0\r
488 Db = GetDB()\r
489 SqlStatement = """ select TimeStamp\r
490 from File\r
491 where FullPath = \'%s\'\r
492 """ % (FullFileName)\r
493 ResultSet = Db.TblFile.Exec(SqlStatement)\r
494 for Result in ResultSet:\r
495 TimeValue = Result[0]\r
496 return TimeValue\r
497\r
498def CollectSourceCodeDataIntoDB(RootDir):\r
499 FileObjList = []\r
500 tuple = os.walk(RootDir)\r
501 IgnoredPattern = GetIgnoredDirListPattern()\r
502 ParseErrorFileList = []\r
503\r
504 for dirpath, dirnames, filenames in tuple:\r
505 if IgnoredPattern.match(dirpath.upper()):\r
506 continue\r
507\r
508 for Dir in dirnames:\r
509 Dirname = os.path.join(dirpath, Dir)\r
510 if os.path.islink(Dirname):\r
511 Dirname = os.path.realpath(Dirname)\r
512 if os.path.isdir(Dirname):\r
513 # symlinks to directories are treated as directories\r
514 dirnames.remove(Dir)\r
515 dirnames.append(Dirname)\r
516\r
517 for f in filenames:\r
8c3f9b4e
HC
518 if f.lower() in EccGlobalData.gConfig.SkipFileList:\r
519 continue\r
e56468c0 520 collector = None\r
30fdf114 521 FullName = os.path.normpath(os.path.join(dirpath, f))\r
e56468c0 522 model = DataClass.MODEL_FILE_OTHERS\r
30fdf114
LG
523 if os.path.splitext(f)[1] in ('.h', '.c'):\r
524 EdkLogger.info("Parsing " + FullName)\r
525 model = f.endswith('c') and DataClass.MODEL_FILE_C or DataClass.MODEL_FILE_H\r
526 collector = CodeFragmentCollector.CodeFragmentCollector(FullName)\r
527 try:\r
528 collector.ParseFile()\r
529 except UnicodeError:\r
530 ParseErrorFileList.append(FullName)\r
531 collector.CleanFileProfileBuffer()\r
532 collector.ParseFileWithClearedPPDirective()\r
533# collector.PrintFragments()\r
e56468c0 534 BaseName = os.path.basename(f)\r
535 DirName = os.path.dirname(FullName)\r
536 Ext = os.path.splitext(f)[1].lstrip('.')\r
537 ModifiedTime = os.path.getmtime(FullName)\r
538 FileObj = DataClass.FileClass(-1, BaseName, Ext, DirName, FullName, model, ModifiedTime, GetFunctionList(), GetIdentifierList(), [])\r
539 FileObjList.append(FileObj)\r
540 if collector:\r
52302d4d
LG
541 collector.CleanFileProfileBuffer()\r
542\r
30fdf114
LG
543 if len(ParseErrorFileList) > 0:\r
544 EdkLogger.info("Found unrecoverable error during parsing:\n\t%s\n" % "\n\t".join(ParseErrorFileList))\r
52302d4d
LG
545\r
546 Db = GetDB()\r
547 for file in FileObjList:\r
e56468c0 548 if file.ExtName.upper() not in ['INF', 'DEC', 'DSC', 'FDF']:\r
549 Db.InsertOneFile(file)\r
30fdf114
LG
550\r
551 Db.UpdateIdentifierBelongsToFunction()\r
552\r
79b74a03 553def GetTableID(FullFileName, ErrorMsgList=None):\r
4231a819 554 if ErrorMsgList is None:\r
30fdf114 555 ErrorMsgList = []\r
52302d4d 556\r
30fdf114
LG
557 Db = GetDB()\r
558 SqlStatement = """ select ID\r
559 from File\r
560 where FullPath like '%s'\r
561 """ % FullFileName\r
30fdf114
LG
562 ResultSet = Db.TblFile.Exec(SqlStatement)\r
563\r
564 FileID = -1\r
565 for Result in ResultSet:\r
566 if FileID != -1:\r
567 ErrorMsgList.append('Duplicate file ID found in DB for file %s' % FullFileName)\r
79b74a03 568 return - 2\r
30fdf114
LG
569 FileID = Result[0]\r
570 if FileID == -1:\r
571 ErrorMsgList.append('NO file ID found in DB for file %s' % FullFileName)\r
79b74a03 572 return - 1\r
30fdf114
LG
573 return FileID\r
574\r
575def GetIncludeFileList(FullFileName):\r
e56468c0 576 if os.path.splitext(FullFileName)[1].upper() not in ('.H'):\r
577 return []\r
30fdf114 578 IFList = IncludeFileListDict.get(FullFileName)\r
4231a819 579 if IFList is not None:\r
30fdf114 580 return IFList\r
52302d4d 581\r
30fdf114
LG
582 FileID = GetTableID(FullFileName)\r
583 if FileID < 0:\r
584 return []\r
52302d4d 585\r
30fdf114
LG
586 Db = GetDB()\r
587 FileTable = 'Identifier' + str(FileID)\r
588 SqlStatement = """ select Value\r
589 from %s\r
590 where Model = %d\r
591 """ % (FileTable, DataClass.MODEL_IDENTIFIER_INCLUDE)\r
592 ResultSet = Db.TblFile.Exec(SqlStatement)\r
593 IncludeFileListDict[FullFileName] = ResultSet\r
594 return ResultSet\r
595\r
596def GetFullPathOfIncludeFile(Str, IncludePathList):\r
597 for IncludePath in IncludePathList:\r
598 FullPath = os.path.join(IncludePath, Str)\r
599 FullPath = os.path.normpath(FullPath)\r
600 if os.path.exists(FullPath):\r
601 return FullPath\r
602 return None\r
603\r
604def GetAllIncludeFiles(FullFileName):\r
4231a819 605 if AllIncludeFileListDict.get(FullFileName) is not None:\r
30fdf114 606 return AllIncludeFileListDict.get(FullFileName)\r
52302d4d 607\r
30fdf114
LG
608 FileDirName = os.path.dirname(FullFileName)\r
609 IncludePathList = IncludePathListDict.get(FileDirName)\r
4231a819 610 if IncludePathList is None:\r
30fdf114
LG
611 IncludePathList = MetaDataParser.GetIncludeListOfFile(EccGlobalData.gWorkspace, FullFileName, GetDB())\r
612 if FileDirName not in IncludePathList:\r
613 IncludePathList.insert(0, FileDirName)\r
614 IncludePathListDict[FileDirName] = IncludePathList\r
615 IncludeFileQueue = []\r
616 for IncludeFile in GetIncludeFileList(FullFileName):\r
617 FileName = IncludeFile[0].lstrip('#').strip()\r
618 FileName = FileName.lstrip('include').strip()\r
619 FileName = FileName.strip('\"')\r
620 FileName = FileName.lstrip('<').rstrip('>').strip()\r
621 FullPath = GetFullPathOfIncludeFile(FileName, IncludePathList)\r
4231a819 622 if FullPath is not None:\r
30fdf114 623 IncludeFileQueue.append(FullPath)\r
52302d4d 624\r
30fdf114
LG
625 i = 0\r
626 while i < len(IncludeFileQueue):\r
627 for IncludeFile in GetIncludeFileList(IncludeFileQueue[i]):\r
628 FileName = IncludeFile[0].lstrip('#').strip()\r
629 FileName = FileName.lstrip('include').strip()\r
630 FileName = FileName.strip('\"')\r
631 FileName = FileName.lstrip('<').rstrip('>').strip()\r
632 FullPath = GetFullPathOfIncludeFile(FileName, IncludePathList)\r
4231a819 633 if FullPath is not None and FullPath not in IncludeFileQueue:\r
30fdf114
LG
634 IncludeFileQueue.insert(i + 1, FullPath)\r
635 i += 1\r
52302d4d 636\r
30fdf114
LG
637 AllIncludeFileListDict[FullFileName] = IncludeFileQueue\r
638 return IncludeFileQueue\r
639\r
640def GetPredicateListFromPredicateExpStr(PES):\r
641\r
642 PredicateList = []\r
643 i = 0\r
644 PredicateBegin = 0\r
645 #PredicateEnd = 0\r
646 LogicOpPos = -1\r
647 p = GetFuncDeclPattern()\r
648 while i < len(PES) - 1:\r
649 if (PES[i].isalnum() or PES[i] == '_' or PES[i] == '*') and LogicOpPos > PredicateBegin:\r
650 PredicateBegin = i\r
79b74a03 651 if (PES[i] == '&' and PES[i + 1] == '&') or (PES[i] == '|' and PES[i + 1] == '|'):\r
30fdf114
LG
652 LogicOpPos = i\r
653 Exp = PES[PredicateBegin:i].strip()\r
654 # Exp may contain '.' or '->'\r
655 TmpExp = Exp.replace('.', '').replace('->', '')\r
656 if p.match(TmpExp):\r
657 PredicateList.append(Exp)\r
658 else:\r
659 PredicateList.append(Exp.rstrip(';').rstrip(')').strip())\r
660 i += 1\r
52302d4d 661\r
30fdf114
LG
662 if PredicateBegin > LogicOpPos:\r
663 while PredicateBegin < len(PES):\r
664 if PES[PredicateBegin].isalnum() or PES[PredicateBegin] == '_' or PES[PredicateBegin] == '*':\r
665 break\r
666 PredicateBegin += 1\r
667 Exp = PES[PredicateBegin:len(PES)].strip()\r
668 # Exp may contain '.' or '->'\r
669 TmpExp = Exp.replace('.', '').replace('->', '')\r
670 if p.match(TmpExp):\r
671 PredicateList.append(Exp)\r
672 else:\r
673 PredicateList.append(Exp.rstrip(';').rstrip(')').strip())\r
674 return PredicateList\r
52302d4d 675\r
79b74a03 676def GetCNameList(Lvalue, StarList=[]):\r
30fdf114
LG
677 Lvalue += ' '\r
678 i = 0\r
679 SearchBegin = 0\r
680 VarStart = -1\r
681 VarEnd = -1\r
682 VarList = []\r
52302d4d 683\r
30fdf114
LG
684 while SearchBegin < len(Lvalue):\r
685 while i < len(Lvalue):\r
686 if Lvalue[i].isalnum() or Lvalue[i] == '_':\r
687 if VarStart == -1:\r
688 VarStart = i\r
689 VarEnd = i\r
690 i += 1\r
691 elif VarEnd != -1:\r
79b74a03 692 VarList.append(Lvalue[VarStart:VarEnd + 1])\r
30fdf114
LG
693 i += 1\r
694 break\r
695 else:\r
696 if VarStart == -1 and Lvalue[i] == '*':\r
697 StarList.append('*')\r
698 i += 1\r
699 if VarEnd == -1:\r
700 break\r
52302d4d
LG
701\r
702\r
30fdf114
LG
703 DotIndex = Lvalue[VarEnd:].find('.')\r
704 ArrowIndex = Lvalue[VarEnd:].find('->')\r
705 if DotIndex == -1 and ArrowIndex == -1:\r
706 break\r
707 elif DotIndex == -1 and ArrowIndex != -1:\r
708 SearchBegin = VarEnd + ArrowIndex\r
709 elif ArrowIndex == -1 and DotIndex != -1:\r
710 SearchBegin = VarEnd + DotIndex\r
711 else:\r
52302d4d
LG
712 SearchBegin = VarEnd + ((DotIndex < ArrowIndex) and DotIndex or ArrowIndex)\r
713\r
30fdf114
LG
714 i = SearchBegin\r
715 VarStart = -1\r
716 VarEnd = -1\r
52302d4d
LG
717\r
718 return VarList\r
30fdf114 719\r
79b74a03 720def SplitPredicateByOp(Str, Op, IsFuncCalling=False):\r
30fdf114
LG
721\r
722 Name = Str.strip()\r
723 Value = None\r
52302d4d 724\r
30fdf114
LG
725 if IsFuncCalling:\r
726 Index = 0\r
727 LBFound = False\r
728 UnmatchedLBCount = 0\r
729 while Index < len(Str):\r
730 while not LBFound and Str[Index] != '_' and not Str[Index].isalnum():\r
731 Index += 1\r
52302d4d 732\r
30fdf114
LG
733 while not LBFound and (Str[Index].isalnum() or Str[Index] == '_'):\r
734 Index += 1\r
735 # maybe type-cast at the begining, skip it.\r
736 RemainingStr = Str[Index:].lstrip()\r
737 if RemainingStr.startswith(')') and not LBFound:\r
738 Index += 1\r
739 continue\r
52302d4d 740\r
30fdf114
LG
741 if RemainingStr.startswith('(') and not LBFound:\r
742 LBFound = True\r
52302d4d 743\r
30fdf114
LG
744 if Str[Index] == '(':\r
745 UnmatchedLBCount += 1\r
746 Index += 1\r
747 continue\r
52302d4d 748\r
30fdf114
LG
749 if Str[Index] == ')':\r
750 UnmatchedLBCount -= 1\r
751 Index += 1\r
752 if UnmatchedLBCount == 0:\r
753 break\r
754 continue\r
52302d4d 755\r
30fdf114 756 Index += 1\r
52302d4d 757\r
30fdf114
LG
758 if UnmatchedLBCount > 0:\r
759 return [Name]\r
52302d4d 760\r
30fdf114
LG
761 IndexInRemainingStr = Str[Index:].find(Op)\r
762 if IndexInRemainingStr == -1:\r
763 return [Name]\r
52302d4d 764\r
30fdf114 765 Name = Str[0:Index + IndexInRemainingStr].strip()\r
79b74a03 766 Value = Str[Index + IndexInRemainingStr + len(Op):].strip().strip(')')\r
30fdf114 767 return [Name, Value]\r
52302d4d 768\r
30fdf114
LG
769 TmpStr = Str.rstrip(';').rstrip(')')\r
770 while True:\r
771 Index = TmpStr.rfind(Op)\r
772 if Index == -1:\r
773 return [Name]\r
52302d4d 774\r
79b74a03 775 if Str[Index - 1].isalnum() or Str[Index - 1].isspace() or Str[Index - 1] == ')' or Str[Index - 1] == ']':\r
30fdf114
LG
776 Name = Str[0:Index].strip()\r
777 Value = Str[Index + len(Op):].strip()\r
52302d4d
LG
778 return [Name, Value]\r
779\r
30fdf114
LG
780 TmpStr = Str[0:Index - 1]\r
781\r
782def SplitPredicateStr(Str):\r
52302d4d
LG
783\r
784 Str = Str.lstrip('(')\r
30fdf114
LG
785 IsFuncCalling = False\r
786 p = GetFuncDeclPattern()\r
787 TmpStr = Str.replace('.', '').replace('->', '')\r
788 if p.match(TmpStr):\r
789 IsFuncCalling = True\r
52302d4d 790\r
30fdf114
LG
791 PredPartList = SplitPredicateByOp(Str, '==', IsFuncCalling)\r
792 if len(PredPartList) > 1:\r
793 return [PredPartList, '==']\r
52302d4d 794\r
30fdf114
LG
795 PredPartList = SplitPredicateByOp(Str, '!=', IsFuncCalling)\r
796 if len(PredPartList) > 1:\r
797 return [PredPartList, '!=']\r
52302d4d 798\r
30fdf114
LG
799 PredPartList = SplitPredicateByOp(Str, '>=', IsFuncCalling)\r
800 if len(PredPartList) > 1:\r
801 return [PredPartList, '>=']\r
52302d4d 802\r
30fdf114
LG
803 PredPartList = SplitPredicateByOp(Str, '<=', IsFuncCalling)\r
804 if len(PredPartList) > 1:\r
805 return [PredPartList, '<=']\r
52302d4d 806\r
30fdf114
LG
807 PredPartList = SplitPredicateByOp(Str, '>', IsFuncCalling)\r
808 if len(PredPartList) > 1:\r
809 return [PredPartList, '>']\r
52302d4d 810\r
30fdf114
LG
811 PredPartList = SplitPredicateByOp(Str, '<', IsFuncCalling)\r
812 if len(PredPartList) > 1:\r
813 return [PredPartList, '<']\r
52302d4d 814\r
30fdf114
LG
815 return [[Str, None], None]\r
816\r
817def GetFuncContainsPE(ExpLine, ResultSet):\r
818 for Result in ResultSet:\r
819 if Result[0] < ExpLine and Result[1] > ExpLine:\r
820 return Result\r
821 return None\r
822\r
823def PatternInModifier(Modifier, SubStr):\r
824 PartList = Modifier.split()\r
825 for Part in PartList:\r
826 if Part == SubStr:\r
827 return True\r
828 return False\r
829\r
830def GetDataTypeFromModifier(ModifierStr):\r
831 MList = ModifierStr.split()\r
79b74a03 832 ReturnType = ''\r
30fdf114 833 for M in MList:\r
eece4292 834 if M in EccGlobalData.gConfig.ModifierSet:\r
79b74a03 835 continue\r
30fdf114 836 # remove array sufix\r
79b74a03
LG
837 if M.startswith('[') or M.endswith(']'):\r
838 continue\r
30fdf114 839 ReturnType += M + ' '\r
52302d4d 840\r
30fdf114
LG
841 ReturnType = ReturnType.strip()\r
842 if len(ReturnType) == 0:\r
843 ReturnType = 'VOID'\r
844 return ReturnType\r
845\r
846def DiffModifier(Str1, Str2):\r
847 PartList1 = Str1.split()\r
848 PartList2 = Str2.split()\r
849 if PartList1 == PartList2:\r
850 return False\r
851 else:\r
852 return True\r
52302d4d 853\r
30fdf114 854def GetTypedefDict(FullFileName):\r
52302d4d 855\r
30fdf114 856 Dict = ComplexTypeDict.get(FullFileName)\r
4231a819 857 if Dict is not None:\r
30fdf114 858 return Dict\r
52302d4d 859\r
30fdf114
LG
860 FileID = GetTableID(FullFileName)\r
861 FileTable = 'Identifier' + str(FileID)\r
862 Db = GetDB()\r
863 SqlStatement = """ select Modifier, Name, Value, ID\r
864 from %s\r
865 where Model = %d\r
866 """ % (FileTable, DataClass.MODEL_IDENTIFIER_TYPEDEF)\r
867 ResultSet = Db.TblFile.Exec(SqlStatement)\r
52302d4d 868\r
30fdf114
LG
869 Dict = {}\r
870 for Result in ResultSet:\r
871 if len(Result[0]) == 0:\r
872 Dict[Result[1]] = Result[2]\r
52302d4d 873\r
30fdf114
LG
874 IncludeFileList = GetAllIncludeFiles(FullFileName)\r
875 for F in IncludeFileList:\r
876 FileID = GetTableID(F)\r
877 if FileID < 0:\r
878 continue\r
52302d4d 879\r
30fdf114
LG
880 FileTable = 'Identifier' + str(FileID)\r
881 SqlStatement = """ select Modifier, Name, Value, ID\r
882 from %s\r
883 where Model = %d\r
884 """ % (FileTable, DataClass.MODEL_IDENTIFIER_TYPEDEF)\r
885 ResultSet = Db.TblFile.Exec(SqlStatement)\r
52302d4d 886\r
30fdf114
LG
887 for Result in ResultSet:\r
888 if not Result[2].startswith('FP ('):\r
889 Dict[Result[1]] = Result[2]\r
890 else:\r
891 if len(Result[0]) == 0:\r
892 Dict[Result[1]] = 'VOID'\r
893 else:\r
894 Dict[Result[1]] = GetDataTypeFromModifier(Result[0])\r
52302d4d 895\r
30fdf114
LG
896 ComplexTypeDict[FullFileName] = Dict\r
897 return Dict\r
898\r
899def GetSUDict(FullFileName):\r
52302d4d 900\r
30fdf114 901 Dict = SUDict.get(FullFileName)\r
4231a819 902 if Dict is not None:\r
30fdf114 903 return Dict\r
52302d4d 904\r
30fdf114
LG
905 FileID = GetTableID(FullFileName)\r
906 FileTable = 'Identifier' + str(FileID)\r
907 Db = GetDB()\r
908 SqlStatement = """ select Name, Value, ID\r
909 from %s\r
910 where Model = %d or Model = %d\r
911 """ % (FileTable, DataClass.MODEL_IDENTIFIER_STRUCTURE, DataClass.MODEL_IDENTIFIER_UNION)\r
912 ResultSet = Db.TblFile.Exec(SqlStatement)\r
52302d4d 913\r
30fdf114
LG
914 Dict = {}\r
915 for Result in ResultSet:\r
916 if len(Result[1]) > 0:\r
917 Dict[Result[0]] = Result[1]\r
52302d4d 918\r
30fdf114
LG
919 IncludeFileList = GetAllIncludeFiles(FullFileName)\r
920 for F in IncludeFileList:\r
921 FileID = GetTableID(F)\r
922 if FileID < 0:\r
923 continue\r
52302d4d 924\r
30fdf114
LG
925 FileTable = 'Identifier' + str(FileID)\r
926 SqlStatement = """ select Name, Value, ID\r
927 from %s\r
928 where Model = %d or Model = %d\r
929 """ % (FileTable, DataClass.MODEL_IDENTIFIER_STRUCTURE, DataClass.MODEL_IDENTIFIER_UNION)\r
930 ResultSet = Db.TblFile.Exec(SqlStatement)\r
52302d4d 931\r
30fdf114
LG
932 for Result in ResultSet:\r
933 if len(Result[1]) > 0:\r
934 Dict[Result[0]] = Result[1]\r
52302d4d 935\r
30fdf114
LG
936 SUDict[FullFileName] = Dict\r
937 return Dict\r
938\r
939def StripComments(Str):\r
940 Str += ' '\r
941 ListFromStr = list(Str)\r
52302d4d 942\r
30fdf114
LG
943 InComment = False\r
944 DoubleSlashComment = False\r
945 Index = 0\r
946 while Index < len(ListFromStr):\r
947 # meet new line, then no longer in a comment for //\r
948 if ListFromStr[Index] == '\n':\r
949 if InComment and DoubleSlashComment:\r
950 InComment = False\r
951 DoubleSlashComment = False\r
952 Index += 1\r
953 # check for */ comment end\r
79b74a03 954 elif InComment and not DoubleSlashComment and ListFromStr[Index] == '*' and ListFromStr[Index + 1] == '/':\r
30fdf114
LG
955 ListFromStr[Index] = ' '\r
956 Index += 1\r
957 ListFromStr[Index] = ' '\r
958 Index += 1\r
959 InComment = False\r
960 # set comments to spaces\r
961 elif InComment:\r
962 ListFromStr[Index] = ' '\r
963 Index += 1\r
964 # check for // comment\r
79b74a03 965 elif ListFromStr[Index] == '/' and ListFromStr[Index + 1] == '/' and ListFromStr[Index + 2] != '\n':\r
30fdf114
LG
966 InComment = True\r
967 DoubleSlashComment = True\r
52302d4d 968\r
30fdf114 969 # check for /* comment start\r
79b74a03 970 elif ListFromStr[Index] == '/' and ListFromStr[Index + 1] == '*':\r
30fdf114
LG
971 ListFromStr[Index] = ' '\r
972 Index += 1\r
973 ListFromStr[Index] = ' '\r
974 Index += 1\r
975 InComment = True\r
976 else:\r
977 Index += 1\r
978\r
979 # restore from List to String\r
980 Str = "".join(ListFromStr)\r
981 Str = Str.rstrip(' ')\r
52302d4d 982\r
30fdf114
LG
983 return Str\r
984\r
985def GetFinalTypeValue(Type, FieldName, TypedefDict, SUDict):\r
986 Value = TypedefDict.get(Type)\r
4231a819 987 if Value is None:\r
30fdf114 988 Value = SUDict.get(Type)\r
4231a819 989 if Value is None:\r
30fdf114 990 return None\r
52302d4d 991\r
30fdf114
LG
992 LBPos = Value.find('{')\r
993 while LBPos == -1:\r
994 FTList = Value.split()\r
995 for FT in FTList:\r
996 if FT not in ('struct', 'union'):\r
997 Value = TypedefDict.get(FT)\r
4231a819 998 if Value is None:\r
30fdf114
LG
999 Value = SUDict.get(FT)\r
1000 break\r
52302d4d 1001\r
4231a819 1002 if Value is None:\r
30fdf114 1003 return None\r
52302d4d 1004\r
30fdf114 1005 LBPos = Value.find('{')\r
52302d4d 1006\r
30fdf114
LG
1007# RBPos = Value.find('}')\r
1008 Fields = Value[LBPos + 1:]\r
1009 Fields = StripComments(Fields)\r
1010 FieldsList = Fields.split(';')\r
1011 for Field in FieldsList:\r
1012 Field = Field.strip()\r
1013 Index = Field.rfind(FieldName)\r
1014 if Index < 1:\r
1015 continue\r
1016 if not Field[Index - 1].isalnum():\r
1017 if Index + len(FieldName) == len(Field):\r
1018 Type = GetDataTypeFromModifier(Field[0:Index])\r
1019 return Type.strip()\r
1020 else:\r
52302d4d 1021 # For the condition that the field in struct is an array with [] sufixes...\r
30fdf114
LG
1022 if not Field[Index + len(FieldName)].isalnum():\r
1023 Type = GetDataTypeFromModifier(Field[0:Index])\r
1024 return Type.strip()\r
52302d4d 1025\r
30fdf114 1026 return None\r
52302d4d 1027\r
79b74a03 1028def GetRealType(Type, TypedefDict, TargetType=None):\r
4231a819 1029 if TargetType is not None and Type == TargetType:\r
30fdf114
LG
1030 return Type\r
1031 while TypedefDict.get(Type):\r
1032 Type = TypedefDict.get(Type)\r
4231a819 1033 if TargetType is not None and Type == TargetType:\r
30fdf114
LG
1034 return Type\r
1035 return Type\r
1036\r
79b74a03 1037def GetTypeInfo(RefList, Modifier, FullFileName, TargetType=None):\r
30fdf114
LG
1038 TypedefDict = GetTypedefDict(FullFileName)\r
1039 SUDict = GetSUDict(FullFileName)\r
1040 Type = GetDataTypeFromModifier(Modifier).replace('*', '').strip()\r
52302d4d 1041\r
30fdf114
LG
1042 Type = Type.split()[-1]\r
1043 Index = 0\r
1044 while Index < len(RefList):\r
1045 FieldName = RefList[Index]\r
1046 FromType = GetFinalTypeValue(Type, FieldName, TypedefDict, SUDict)\r
4231a819 1047 if FromType is None:\r
30fdf114
LG
1048 return None\r
1049 # we want to determine the exact type.\r
4231a819 1050 if TargetType is not None:\r
30fdf114
LG
1051 Type = FromType.split()[0]\r
1052 # we only want to check if it is a pointer\r
1053 else:\r
1054 Type = FromType\r
79b74a03 1055 if Type.find('*') != -1 and Index == len(RefList) - 1:\r
30fdf114
LG
1056 return Type\r
1057 Type = FromType.split()[0]\r
52302d4d 1058\r
30fdf114
LG
1059 Index += 1\r
1060\r
1061 Type = GetRealType(Type, TypedefDict, TargetType)\r
1062\r
1063 return Type\r
1064\r
79b74a03 1065def GetVarInfo(PredVarList, FuncRecord, FullFileName, IsFuncCall=False, TargetType=None, StarList=None):\r
52302d4d 1066\r
30fdf114
LG
1067 PredVar = PredVarList[0]\r
1068 FileID = GetTableID(FullFileName)\r
52302d4d 1069\r
30fdf114
LG
1070 Db = GetDB()\r
1071 FileTable = 'Identifier' + str(FileID)\r
1072 # search variable in include files\r
52302d4d 1073\r
30fdf114
LG
1074 # it is a function call, search function declarations and definitions\r
1075 if IsFuncCall:\r
1076 SqlStatement = """ select Modifier, ID\r
1077 from %s\r
1078 where Model = %d and Value = \'%s\'\r
1079 """ % (FileTable, DataClass.MODEL_IDENTIFIER_FUNCTION_DECLARATION, PredVar)\r
1080 ResultSet = Db.TblFile.Exec(SqlStatement)\r
52302d4d
LG
1081\r
1082 for Result in ResultSet:\r
30fdf114
LG
1083 Type = GetDataTypeFromModifier(Result[0]).split()[-1]\r
1084 TypedefDict = GetTypedefDict(FullFileName)\r
1085 Type = GetRealType(Type, TypedefDict, TargetType)\r
1086 return Type\r
52302d4d 1087\r
30fdf114
LG
1088 IncludeFileList = GetAllIncludeFiles(FullFileName)\r
1089 for F in IncludeFileList:\r
1090 FileID = GetTableID(F)\r
1091 if FileID < 0:\r
1092 continue\r
52302d4d 1093\r
30fdf114
LG
1094 FileTable = 'Identifier' + str(FileID)\r
1095 SqlStatement = """ select Modifier, ID\r
1096 from %s\r
1097 where Model = %d and Value = \'%s\'\r
1098 """ % (FileTable, DataClass.MODEL_IDENTIFIER_FUNCTION_DECLARATION, PredVar)\r
1099 ResultSet = Db.TblFile.Exec(SqlStatement)\r
52302d4d 1100\r
30fdf114
LG
1101 for Result in ResultSet:\r
1102 Type = GetDataTypeFromModifier(Result[0]).split()[-1]\r
1103 TypedefDict = GetTypedefDict(FullFileName)\r
1104 Type = GetRealType(Type, TypedefDict, TargetType)\r
1105 return Type\r
52302d4d 1106\r
30fdf114
LG
1107 FileID = GetTableID(FullFileName)\r
1108 SqlStatement = """ select Modifier, ID\r
1109 from Function\r
1110 where BelongsToFile = %d and Name = \'%s\'\r
1111 """ % (FileID, PredVar)\r
1112 ResultSet = Db.TblFile.Exec(SqlStatement)\r
52302d4d
LG
1113\r
1114 for Result in ResultSet:\r
30fdf114
LG
1115 Type = GetDataTypeFromModifier(Result[0]).split()[-1]\r
1116 TypedefDict = GetTypedefDict(FullFileName)\r
1117 Type = GetRealType(Type, TypedefDict, TargetType)\r
1118 return Type\r
52302d4d 1119\r
30fdf114
LG
1120 for F in IncludeFileList:\r
1121 FileID = GetTableID(F)\r
1122 if FileID < 0:\r
1123 continue\r
52302d4d 1124\r
30fdf114
LG
1125 FileTable = 'Identifier' + str(FileID)\r
1126 SqlStatement = """ select Modifier, ID\r
1127 from Function\r
1128 where BelongsToFile = %d and Name = \'%s\'\r
1129 """ % (FileID, PredVar)\r
1130 ResultSet = Db.TblFile.Exec(SqlStatement)\r
52302d4d 1131\r
30fdf114
LG
1132 for Result in ResultSet:\r
1133 Type = GetDataTypeFromModifier(Result[0]).split()[-1]\r
1134 TypedefDict = GetTypedefDict(FullFileName)\r
1135 Type = GetRealType(Type, TypedefDict, TargetType)\r
1136 return Type\r
52302d4d 1137\r
30fdf114 1138 return None\r
52302d4d 1139\r
30fdf114
LG
1140 # really variable, search local variable first\r
1141 SqlStatement = """ select Modifier, ID\r
1142 from %s\r
1143 where Model = %d and Name = \'%s\' and StartLine >= %d and StartLine <= %d\r
1144 """ % (FileTable, DataClass.MODEL_IDENTIFIER_VARIABLE, PredVar, FuncRecord[0], FuncRecord[1])\r
1145 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1146 VarFound = False\r
1147 for Result in ResultSet:\r
1148 if len(PredVarList) > 1:\r
1149 Type = GetTypeInfo(PredVarList[1:], Result[0], FullFileName, TargetType)\r
1150 return Type\r
1151 else:\r
1152# Type = GetDataTypeFromModifier(Result[0]).split()[-1]\r
1153 TypeList = GetDataTypeFromModifier(Result[0]).split()\r
1154 Type = TypeList[-1]\r
4231a819 1155 if len(TypeList) > 1 and StarList is not None:\r
30fdf114
LG
1156 for Star in StarList:\r
1157 Type = Type.strip()\r
1158 Type = Type.rstrip(Star)\r
1159 # Get real type after de-reference pointers.\r
1160 if len(Type.strip()) == 0:\r
1161 Type = TypeList[-2]\r
1162 TypedefDict = GetTypedefDict(FullFileName)\r
1163 Type = GetRealType(Type, TypedefDict, TargetType)\r
1164 return Type\r
52302d4d 1165\r
30fdf114
LG
1166 # search function parameters second\r
1167 ParamList = GetParamList(FuncRecord[2])\r
1168 for Param in ParamList:\r
1169 if Param.Name.strip() == PredVar:\r
1170 if len(PredVarList) > 1:\r
1171 Type = GetTypeInfo(PredVarList[1:], Param.Modifier, FullFileName, TargetType)\r
1172 return Type\r
1173 else:\r
1174 TypeList = GetDataTypeFromModifier(Param.Modifier).split()\r
1175 Type = TypeList[-1]\r
83461d2c
HC
1176 if Type == '*' and len(TypeList) >= 2:\r
1177 Type = TypeList[-2]\r
4231a819 1178 if len(TypeList) > 1 and StarList is not None:\r
30fdf114
LG
1179 for Star in StarList:\r
1180 Type = Type.strip()\r
1181 Type = Type.rstrip(Star)\r
1182 # Get real type after de-reference pointers.\r
1183 if len(Type.strip()) == 0:\r
1184 Type = TypeList[-2]\r
1185 TypedefDict = GetTypedefDict(FullFileName)\r
1186 Type = GetRealType(Type, TypedefDict, TargetType)\r
1187 return Type\r
52302d4d 1188\r
30fdf114
LG
1189 # search global variable next\r
1190 SqlStatement = """ select Modifier, ID\r
1191 from %s\r
1192 where Model = %d and Name = \'%s\' and BelongsToFunction = -1\r
1193 """ % (FileTable, DataClass.MODEL_IDENTIFIER_VARIABLE, PredVar)\r
1194 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1195\r
1196 for Result in ResultSet:\r
1197 if len(PredVarList) > 1:\r
1198 Type = GetTypeInfo(PredVarList[1:], Result[0], FullFileName, TargetType)\r
1199 return Type\r
1200 else:\r
1201 TypeList = GetDataTypeFromModifier(Result[0]).split()\r
1202 Type = TypeList[-1]\r
4231a819 1203 if len(TypeList) > 1 and StarList is not None:\r
30fdf114
LG
1204 for Star in StarList:\r
1205 Type = Type.strip()\r
1206 Type = Type.rstrip(Star)\r
1207 # Get real type after de-reference pointers.\r
1208 if len(Type.strip()) == 0:\r
1209 Type = TypeList[-2]\r
1210 TypedefDict = GetTypedefDict(FullFileName)\r
1211 Type = GetRealType(Type, TypedefDict, TargetType)\r
1212 return Type\r
52302d4d 1213\r
30fdf114
LG
1214 IncludeFileList = GetAllIncludeFiles(FullFileName)\r
1215 for F in IncludeFileList:\r
1216 FileID = GetTableID(F)\r
1217 if FileID < 0:\r
1218 continue\r
52302d4d 1219\r
30fdf114
LG
1220 FileTable = 'Identifier' + str(FileID)\r
1221 SqlStatement = """ select Modifier, ID\r
1222 from %s\r
1223 where Model = %d and BelongsToFunction = -1 and Name = \'%s\'\r
1224 """ % (FileTable, DataClass.MODEL_IDENTIFIER_VARIABLE, PredVar)\r
1225 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1226\r
1227 for Result in ResultSet:\r
1228 if len(PredVarList) > 1:\r
1229 Type = GetTypeInfo(PredVarList[1:], Result[0], FullFileName, TargetType)\r
1230 return Type\r
1231 else:\r
1232 TypeList = GetDataTypeFromModifier(Result[0]).split()\r
1233 Type = TypeList[-1]\r
4231a819 1234 if len(TypeList) > 1 and StarList is not None:\r
30fdf114
LG
1235 for Star in StarList:\r
1236 Type = Type.strip()\r
1237 Type = Type.rstrip(Star)\r
1238 # Get real type after de-reference pointers.\r
1239 if len(Type.strip()) == 0:\r
1240 Type = TypeList[-2]\r
1241 TypedefDict = GetTypedefDict(FullFileName)\r
1242 Type = GetRealType(Type, TypedefDict, TargetType)\r
1243 return Type\r
1244\r
52302d4d
LG
1245def GetTypeFromArray(Type, Var):\r
1246 Count = Var.count('[')\r
1247\r
1248 while Count > 0:\r
1249 Type = Type.strip()\r
1250 Type = Type.rstrip('*')\r
1251 Count = Count - 1\r
1252\r
1253 return Type\r
1254\r
30fdf114
LG
1255def CheckFuncLayoutReturnType(FullFileName):\r
1256 ErrorMsgList = []\r
52302d4d 1257\r
30fdf114
LG
1258 FileID = GetTableID(FullFileName, ErrorMsgList)\r
1259 if FileID < 0:\r
1260 return ErrorMsgList\r
52302d4d 1261\r
30fdf114
LG
1262 Db = GetDB()\r
1263 FileTable = 'Identifier' + str(FileID)\r
52302d4d 1264 SqlStatement = """ select Modifier, ID, StartLine, StartColumn, EndLine, Value\r
30fdf114
LG
1265 from %s\r
1266 where Model = %d\r
1267 """ % (FileTable, DataClass.MODEL_IDENTIFIER_FUNCTION_DECLARATION)\r
1268 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1269 for Result in ResultSet:\r
1270 ReturnType = GetDataTypeFromModifier(Result[0])\r
1271 TypeStart = ReturnType.split()[0]\r
1272 FuncName = Result[5]\r
1273 if EccGlobalData.gException.IsException(ERROR_C_FUNCTION_LAYOUT_CHECK_RETURN_TYPE, FuncName):\r
1274 continue\r
00261e1d
HC
1275 Result0 = Result[0]\r
1276 if Result0.upper().startswith('STATIC'):\r
1277 Result0 = Result0[6:].strip()\r
1278 Index = Result0.find(TypeStart)\r
30fdf114
LG
1279 if Index != 0 or Result[3] != 0:\r
1280 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_RETURN_TYPE, '[%s] Return Type should appear at the start of line' % FuncName, FileTable, Result[1])\r
52302d4d 1281\r
30fdf114
LG
1282 if Result[2] == Result[4]:\r
1283 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_RETURN_TYPE, '[%s] Return Type should appear on its own line' % FuncName, FileTable, Result[1])\r
52302d4d 1284\r
30fdf114
LG
1285 SqlStatement = """ select Modifier, ID, StartLine, StartColumn, FunNameStartLine, Name\r
1286 from Function\r
1287 where BelongsToFile = %d\r
1288 """ % (FileID)\r
1289 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1290 for Result in ResultSet:\r
1291 ReturnType = GetDataTypeFromModifier(Result[0])\r
1292 TypeStart = ReturnType.split()[0]\r
1293 FuncName = Result[5]\r
1294 if EccGlobalData.gException.IsException(ERROR_C_FUNCTION_LAYOUT_CHECK_RETURN_TYPE, FuncName):\r
1295 continue\r
72358997
HC
1296 Result0 = Result[0]\r
1297 if Result0.upper().startswith('STATIC'):\r
1298 Result0 = Result0[6:].strip()\r
1299 Index = Result0.find(ReturnType)\r
30fdf114
LG
1300 if Index != 0 or Result[3] != 0:\r
1301 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_RETURN_TYPE, '[%s] Return Type should appear at the start of line' % FuncName, 'Function', Result[1])\r
52302d4d 1302\r
30fdf114
LG
1303def CheckFuncLayoutModifier(FullFileName):\r
1304 ErrorMsgList = []\r
52302d4d 1305\r
30fdf114
LG
1306 FileID = GetTableID(FullFileName, ErrorMsgList)\r
1307 if FileID < 0:\r
1308 return ErrorMsgList\r
52302d4d 1309\r
30fdf114
LG
1310 Db = GetDB()\r
1311 FileTable = 'Identifier' + str(FileID)\r
1312 SqlStatement = """ select Modifier, ID\r
1313 from %s\r
1314 where Model = %d\r
1315 """ % (FileTable, DataClass.MODEL_IDENTIFIER_FUNCTION_DECLARATION)\r
1316 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1317 for Result in ResultSet:\r
1318 ReturnType = GetDataTypeFromModifier(Result[0])\r
1319 TypeStart = ReturnType.split()[0]\r
00261e1d
HC
1320 Result0 = Result[0]\r
1321 if Result0.upper().startswith('STATIC'):\r
1322 Result0 = Result0[6:].strip()\r
1323 Index = Result0.find(TypeStart)\r
30fdf114
LG
1324 if Index != 0:\r
1325 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_OPTIONAL_FUNCTIONAL_MODIFIER, '', FileTable, Result[1])\r
52302d4d 1326\r
30fdf114
LG
1327 SqlStatement = """ select Modifier, ID\r
1328 from Function\r
1329 where BelongsToFile = %d\r
1330 """ % (FileID)\r
1331 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1332 for Result in ResultSet:\r
1333 ReturnType = GetDataTypeFromModifier(Result[0])\r
1334 TypeStart = ReturnType.split()[0]\r
72358997
HC
1335 Result0 = Result[0]\r
1336 if Result0.upper().startswith('STATIC'):\r
1337 Result0 = Result0[6:].strip()\r
1338 Index = Result0.find(TypeStart)\r
30fdf114
LG
1339 if Index != 0:\r
1340 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_OPTIONAL_FUNCTIONAL_MODIFIER, '', 'Function', Result[1])\r
1341\r
1342def CheckFuncLayoutName(FullFileName):\r
1343 ErrorMsgList = []\r
1344 # Parameter variable format pattern.\r
1345 Pattern = re.compile(r'^[A-Z]+\S*[a-z]\S*$')\r
1346 ParamIgnoreList = ('VOID', '...')\r
1347 FileID = GetTableID(FullFileName, ErrorMsgList)\r
1348 if FileID < 0:\r
1349 return ErrorMsgList\r
52302d4d 1350\r
30fdf114
LG
1351 Db = GetDB()\r
1352 FileTable = 'Identifier' + str(FileID)\r
1353 SqlStatement = """ select Name, ID, EndColumn, Value\r
1354 from %s\r
1355 where Model = %d\r
1356 """ % (FileTable, DataClass.MODEL_IDENTIFIER_FUNCTION_DECLARATION)\r
1357 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1358 for Result in ResultSet:\r
1359 FuncName = Result[3]\r
1360 if EccGlobalData.gException.IsException(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_NAME, FuncName):\r
1361 continue\r
1362 if Result[2] != 0:\r
1363 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_NAME, 'Function name [%s] should appear at the start of a line' % FuncName, FileTable, Result[1])\r
1364 ParamList = GetParamList(Result[0])\r
1365 if len(ParamList) == 0:\r
1366 continue\r
1367 StartLine = 0\r
1368 for Param in ParamList:\r
1369 if Param.StartLine <= StartLine:\r
1370 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_NAME, 'Parameter %s should be in its own line.' % Param.Name, FileTable, Result[1])\r
1371 if Param.StartLine - StartLine > 1:\r
52302d4d 1372 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_NAME, 'Empty line appears before Parameter %s.' % Param.Name, FileTable, Result[1])\r
30fdf114
LG
1373 if not Pattern.match(Param.Name) and not Param.Name in ParamIgnoreList and not EccGlobalData.gException.IsException(ERROR_NAMING_CONVENTION_CHECK_VARIABLE_NAME, Param.Name):\r
1374 PrintErrorMsg(ERROR_NAMING_CONVENTION_CHECK_VARIABLE_NAME, 'Parameter [%s] NOT follow naming convention.' % Param.Name, FileTable, Result[1])\r
1375 StartLine = Param.StartLine\r
52302d4d 1376\r
30fdf114
LG
1377 if not Result[0].endswith('\n )') and not Result[0].endswith('\r )'):\r
1378 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_NAME, '\')\' should be on a new line and indented two spaces', FileTable, Result[1])\r
52302d4d 1379\r
30fdf114
LG
1380 SqlStatement = """ select Modifier, ID, FunNameStartColumn, Name\r
1381 from Function\r
1382 where BelongsToFile = %d\r
1383 """ % (FileID)\r
1384 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1385 for Result in ResultSet:\r
1386 FuncName = Result[3]\r
1387 if EccGlobalData.gException.IsException(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_NAME, FuncName):\r
1388 continue\r
1389 if Result[2] != 0:\r
1390 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_NAME, 'Function name [%s] should appear at the start of a line' % FuncName, 'Function', Result[1])\r
1391 ParamList = GetParamList(Result[0])\r
1392 if len(ParamList) == 0:\r
1393 continue\r
1394 StartLine = 0\r
1395 for Param in ParamList:\r
1396 if Param.StartLine <= StartLine:\r
1397 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_NAME, 'Parameter %s should be in its own line.' % Param.Name, 'Function', Result[1])\r
1398 if Param.StartLine - StartLine > 1:\r
1399 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_NAME, 'Empty line appears before Parameter %s.' % Param.Name, 'Function', Result[1])\r
1400 if not Pattern.match(Param.Name) and not Param.Name in ParamIgnoreList and not EccGlobalData.gException.IsException(ERROR_NAMING_CONVENTION_CHECK_VARIABLE_NAME, Param.Name):\r
1401 PrintErrorMsg(ERROR_NAMING_CONVENTION_CHECK_VARIABLE_NAME, 'Parameter [%s] NOT follow naming convention.' % Param.Name, FileTable, Result[1])\r
1402 StartLine = Param.StartLine\r
1403 if not Result[0].endswith('\n )') and not Result[0].endswith('\r )'):\r
1404 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_NAME, '\')\' should be on a new line and indented two spaces', 'Function', Result[1])\r
1405\r
1406def CheckFuncLayoutPrototype(FullFileName):\r
1407 ErrorMsgList = []\r
52302d4d 1408\r
30fdf114
LG
1409 FileID = GetTableID(FullFileName, ErrorMsgList)\r
1410 if FileID < 0:\r
1411 return ErrorMsgList\r
52302d4d 1412\r
30fdf114
LG
1413 FileTable = 'Identifier' + str(FileID)\r
1414 Db = GetDB()\r
1415 SqlStatement = """ select Modifier, Header, Name, ID\r
1416 from Function\r
1417 where BelongsToFile = %d\r
1418 """ % (FileID)\r
1419 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1420 if len(ResultSet) == 0:\r
1421 return ErrorMsgList\r
52302d4d 1422\r
30fdf114
LG
1423 FuncDefList = []\r
1424 for Result in ResultSet:\r
1425 FuncDefList.append(Result)\r
52302d4d 1426\r
30fdf114
LG
1427 SqlStatement = """ select Modifier, Name, ID\r
1428 from %s\r
1429 where Model = %d\r
1430 """ % (FileTable, DataClass.MODEL_IDENTIFIER_FUNCTION_DECLARATION)\r
1431 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1432 FuncDeclList = []\r
1433 for Result in ResultSet:\r
1434 FuncDeclList.append(Result)\r
52302d4d 1435\r
30fdf114
LG
1436 UndeclFuncList = []\r
1437 for FuncDef in FuncDefList:\r
1438 FuncName = FuncDef[2].strip()\r
1439 FuncModifier = FuncDef[0]\r
1440 FuncDefHeader = FuncDef[1]\r
1441 for FuncDecl in FuncDeclList:\r
1442 LBPos = FuncDecl[1].find('(')\r
1443 DeclName = FuncDecl[1][0:LBPos].strip()\r
1444 DeclModifier = FuncDecl[0]\r
1445 if DeclName == FuncName:\r
1446 if DiffModifier(FuncModifier, DeclModifier) and not EccGlobalData.gException.IsException(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_PROTO_TYPE, FuncName):\r
1447 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_PROTO_TYPE, 'Function [%s] modifier different with prototype.' % FuncName, 'Function', FuncDef[3])\r
1448 ParamListOfDef = GetParamList(FuncDefHeader)\r
1449 ParamListOfDecl = GetParamList(FuncDecl[1])\r
52302d4d
LG
1450 if len(ParamListOfDef) != len(ParamListOfDecl) and not EccGlobalData.gException.IsException(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_PROTO_TYPE_2, FuncName):\r
1451 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_PROTO_TYPE_2, 'Parameter number different in function [%s].' % FuncName, 'Function', FuncDef[3])\r
30fdf114
LG
1452 break\r
1453\r
1454 Index = 0\r
1455 while Index < len(ParamListOfDef):\r
52302d4d
LG
1456 if DiffModifier(ParamListOfDef[Index].Modifier, ParamListOfDecl[Index].Modifier) and not EccGlobalData.gException.IsException(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_PROTO_TYPE_3, FuncName):\r
1457 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_PROTO_TYPE_3, 'Parameter %s has different modifier with prototype in function [%s].' % (ParamListOfDef[Index].Name, FuncName), 'Function', FuncDef[3])\r
30fdf114
LG
1458 Index += 1\r
1459 break\r
1460 else:\r
1461 UndeclFuncList.append(FuncDef)\r
52302d4d 1462\r
30fdf114
LG
1463 IncludeFileList = GetAllIncludeFiles(FullFileName)\r
1464 FuncDeclList = []\r
1465 for F in IncludeFileList:\r
1466 FileID = GetTableID(F, ErrorMsgList)\r
1467 if FileID < 0:\r
1468 continue\r
52302d4d 1469\r
30fdf114
LG
1470 FileTable = 'Identifier' + str(FileID)\r
1471 SqlStatement = """ select Modifier, Name, ID\r
1472 from %s\r
1473 where Model = %d\r
1474 """ % (FileTable, DataClass.MODEL_IDENTIFIER_FUNCTION_DECLARATION)\r
1475 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1476\r
1477 for Result in ResultSet:\r
1478 FuncDeclList.append(Result)\r
52302d4d 1479\r
30fdf114
LG
1480 for FuncDef in UndeclFuncList:\r
1481 FuncName = FuncDef[2].strip()\r
1482 FuncModifier = FuncDef[0]\r
1483 FuncDefHeader = FuncDef[1]\r
1484 for FuncDecl in FuncDeclList:\r
1485 LBPos = FuncDecl[1].find('(')\r
1486 DeclName = FuncDecl[1][0:LBPos].strip()\r
1487 DeclModifier = FuncDecl[0]\r
1488 if DeclName == FuncName:\r
1489 if DiffModifier(FuncModifier, DeclModifier) and not EccGlobalData.gException.IsException(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_PROTO_TYPE, FuncName):\r
1490 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_PROTO_TYPE, 'Function [%s] modifier different with prototype.' % FuncName, 'Function', FuncDef[3])\r
1491 ParamListOfDef = GetParamList(FuncDefHeader)\r
1492 ParamListOfDecl = GetParamList(FuncDecl[1])\r
52302d4d
LG
1493 if len(ParamListOfDef) != len(ParamListOfDecl) and not EccGlobalData.gException.IsException(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_PROTO_TYPE_2, FuncName):\r
1494 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_PROTO_TYPE_2, 'Parameter number different in function [%s].' % FuncName, 'Function', FuncDef[3])\r
30fdf114
LG
1495 break\r
1496\r
1497 Index = 0\r
1498 while Index < len(ParamListOfDef):\r
52302d4d
LG
1499 if DiffModifier(ParamListOfDef[Index].Modifier, ParamListOfDecl[Index].Modifier) and not EccGlobalData.gException.IsException(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_PROTO_TYPE_3, FuncName):\r
1500 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_PROTO_TYPE_3, 'Parameter %s has different modifier with prototype in function [%s].' % (ParamListOfDef[Index].Name, FuncName), 'Function', FuncDef[3])\r
30fdf114
LG
1501 Index += 1\r
1502 break\r
52302d4d 1503\r
30fdf114
LG
1504def CheckFuncLayoutBody(FullFileName):\r
1505 ErrorMsgList = []\r
52302d4d 1506\r
30fdf114
LG
1507 FileID = GetTableID(FullFileName, ErrorMsgList)\r
1508 if FileID < 0:\r
1509 return ErrorMsgList\r
52302d4d 1510\r
30fdf114
LG
1511 FileTable = 'Identifier' + str(FileID)\r
1512 Db = GetDB()\r
1513 SqlStatement = """ select BodyStartColumn, EndColumn, ID\r
1514 from Function\r
1515 where BelongsToFile = %d\r
1516 """ % (FileID)\r
1517 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1518 if len(ResultSet) == 0:\r
1519 return ErrorMsgList\r
1520 for Result in ResultSet:\r
1521 if Result[0] != 0:\r
1522 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_BODY, 'open brace should be at the very beginning of a line.', 'Function', Result[2])\r
1523 if Result[1] != 0:\r
1524 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_FUNCTION_BODY, 'close brace should be at the very beginning of a line.', 'Function', Result[2])\r
1525\r
1526def CheckFuncLayoutLocalVariable(FullFileName):\r
1527 ErrorMsgList = []\r
52302d4d 1528\r
30fdf114
LG
1529 FileID = GetTableID(FullFileName, ErrorMsgList)\r
1530 if FileID < 0:\r
1531 return ErrorMsgList\r
52302d4d 1532\r
30fdf114
LG
1533 Db = GetDB()\r
1534 FileTable = 'Identifier' + str(FileID)\r
1535 SqlStatement = """ select ID\r
1536 from Function\r
1537 where BelongsToFile = %d\r
1538 """ % (FileID)\r
1539 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1540 if len(ResultSet) == 0:\r
1541 return ErrorMsgList\r
1542 FL = []\r
1543 for Result in ResultSet:\r
1544 FL.append(Result)\r
52302d4d 1545\r
30fdf114 1546 for F in FL:\r
79b74a03 1547 SqlStatement = """ select Name, Value, ID, Modifier\r
30fdf114
LG
1548 from %s\r
1549 where Model = %d and BelongsToFunction = %d\r
1550 """ % (FileTable, DataClass.MODEL_IDENTIFIER_VARIABLE, F[0])\r
1551 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1552 if len(ResultSet) == 0:\r
1553 continue\r
52302d4d 1554\r
30fdf114 1555 for Result in ResultSet:\r
79b74a03 1556 if len(Result[1]) > 0 and 'CONST' not in Result[3]:\r
30fdf114 1557 PrintErrorMsg(ERROR_C_FUNCTION_LAYOUT_CHECK_NO_INIT_OF_VARIABLE, 'Variable Name: %s' % Result[0], FileTable, Result[2])\r
52302d4d 1558\r
30fdf114
LG
1559def CheckMemberVariableFormat(Name, Value, FileTable, TdId, ModelId):\r
1560 ErrMsgList = []\r
1561 # Member variable format pattern.\r
1562 Pattern = re.compile(r'^[A-Z]+\S*[a-z]\S*$')\r
52302d4d 1563\r
30fdf114
LG
1564 LBPos = Value.find('{')\r
1565 RBPos = Value.rfind('}')\r
1566 if LBPos == -1 or RBPos == -1:\r
1567 return ErrMsgList\r
52302d4d 1568\r
30fdf114
LG
1569 Fields = Value[LBPos + 1 : RBPos]\r
1570 Fields = StripComments(Fields).strip()\r
1571 NestPos = Fields.find ('struct')\r
f8895c2a 1572 if NestPos != -1 and (NestPos + len('struct') < len(Fields)) and ModelId != DataClass.MODEL_IDENTIFIER_UNION:\r
30fdf114
LG
1573 if not Fields[NestPos + len('struct') + 1].isalnum():\r
1574 if not EccGlobalData.gException.IsException(ERROR_DECLARATION_DATA_TYPE_CHECK_NESTED_STRUCTURE, Name):\r
1575 PrintErrorMsg(ERROR_DECLARATION_DATA_TYPE_CHECK_NESTED_STRUCTURE, 'Nested struct in [%s].' % (Name), FileTable, TdId)\r
1576 return ErrMsgList\r
1577 NestPos = Fields.find ('union')\r
1578 if NestPos != -1 and (NestPos + len('union') < len(Fields)):\r
1579 if not Fields[NestPos + len('union') + 1].isalnum():\r
1580 if not EccGlobalData.gException.IsException(ERROR_DECLARATION_DATA_TYPE_CHECK_NESTED_STRUCTURE, Name):\r
1581 PrintErrorMsg(ERROR_DECLARATION_DATA_TYPE_CHECK_NESTED_STRUCTURE, 'Nested union in [%s].' % (Name), FileTable, TdId)\r
1582 return ErrMsgList\r
1583 NestPos = Fields.find ('enum')\r
1584 if NestPos != -1 and (NestPos + len('enum') < len(Fields)):\r
1585 if not Fields[NestPos + len('enum') + 1].isalnum():\r
1586 if not EccGlobalData.gException.IsException(ERROR_DECLARATION_DATA_TYPE_CHECK_NESTED_STRUCTURE, Name):\r
1587 PrintErrorMsg(ERROR_DECLARATION_DATA_TYPE_CHECK_NESTED_STRUCTURE, 'Nested enum in [%s].' % (Name), FileTable, TdId)\r
1588 return ErrMsgList\r
52302d4d 1589\r
30fdf114
LG
1590 if ModelId == DataClass.MODEL_IDENTIFIER_ENUMERATE:\r
1591 FieldsList = Fields.split(',')\r
1592 # deal with enum is pre-assigned a value by function call ( , , , ...)\r
1593 QuoteCount = 0\r
1594 Index = 0\r
1595 RemoveCurrentElement = False\r
1596 while Index < len(FieldsList):\r
1597 Field = FieldsList[Index]\r
52302d4d 1598\r
30fdf114
LG
1599 if Field.find('(') != -1:\r
1600 QuoteCount += 1\r
1601 RemoveCurrentElement = True\r
1602 Index += 1\r
1603 continue\r
52302d4d 1604\r
30fdf114
LG
1605 if Field.find(')') != -1 and QuoteCount > 0:\r
1606 QuoteCount -= 1\r
1607\r
52302d4d 1608 if RemoveCurrentElement:\r
30fdf114
LG
1609 FieldsList.remove(Field)\r
1610 if QuoteCount == 0:\r
1611 RemoveCurrentElement = False\r
1612 continue\r
52302d4d 1613\r
30fdf114
LG
1614 if QuoteCount == 0:\r
1615 RemoveCurrentElement = False\r
52302d4d 1616\r
30fdf114
LG
1617 Index += 1\r
1618 else:\r
1619 FieldsList = Fields.split(';')\r
52302d4d 1620\r
30fdf114
LG
1621 for Field in FieldsList:\r
1622 Field = Field.strip()\r
1623 if Field == '':\r
1624 continue\r
52302d4d 1625 # For the condition that the field in struct is an array with [] sufixes...\r
30fdf114
LG
1626 if Field[-1] == ']':\r
1627 LBPos = Field.find('[')\r
1628 Field = Field[0:LBPos]\r
1629 # For the condition that bit field ": Number"\r
1630 if Field.find(':') != -1:\r
1631 ColonPos = Field.find(':')\r
1632 Field = Field[0:ColonPos]\r
52302d4d 1633\r
30fdf114
LG
1634 Field = Field.strip()\r
1635 if Field == '':\r
1636 continue\r
00261e1d
HC
1637 if Field.startswith("#"):\r
1638 continue\r
30fdf114
LG
1639 # Enum could directly assign value to variable\r
1640 Field = Field.split('=')[0].strip()\r
52302d4d 1641 TokenList = Field.split()\r
30fdf114 1642 # Remove pointers before variable\r
fa3a2156
HC
1643 Token = TokenList[-1]\r
1644 if Token in ['OPTIONAL']:\r
1645 Token = TokenList[-2]\r
1646 if not Pattern.match(Token.lstrip('*')):\r
1647 ErrMsgList.append(Token.lstrip('*'))\r
52302d4d 1648\r
30fdf114
LG
1649 return ErrMsgList\r
1650\r
1651def CheckDeclTypedefFormat(FullFileName, ModelId):\r
1652 ErrorMsgList = []\r
52302d4d 1653\r
30fdf114
LG
1654 FileID = GetTableID(FullFileName, ErrorMsgList)\r
1655 if FileID < 0:\r
1656 return ErrorMsgList\r
52302d4d 1657\r
30fdf114
LG
1658 Db = GetDB()\r
1659 FileTable = 'Identifier' + str(FileID)\r
1660 SqlStatement = """ select Name, StartLine, EndLine, ID, Value\r
1661 from %s\r
1662 where Model = %d\r
1663 """ % (FileTable, ModelId)\r
1664 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1665 ResultList = []\r
1666 for Result in ResultSet:\r
1667 ResultList.append(Result)\r
52302d4d 1668\r
30fdf114
LG
1669 ErrorType = ERROR_DECLARATION_DATA_TYPE_CHECK_ALL\r
1670 if ModelId == DataClass.MODEL_IDENTIFIER_STRUCTURE:\r
1671 ErrorType = ERROR_DECLARATION_DATA_TYPE_CHECK_STRUCTURE_DECLARATION\r
1672 elif ModelId == DataClass.MODEL_IDENTIFIER_ENUMERATE:\r
1673 ErrorType = ERROR_DECLARATION_DATA_TYPE_CHECK_ENUMERATED_TYPE\r
1674 elif ModelId == DataClass.MODEL_IDENTIFIER_UNION:\r
1675 ErrorType = ERROR_DECLARATION_DATA_TYPE_CHECK_UNION_TYPE\r
52302d4d 1676\r
30fdf114
LG
1677 SqlStatement = """ select Modifier, Name, Value, StartLine, EndLine, ID\r
1678 from %s\r
1679 where Model = %d\r
1680 """ % (FileTable, DataClass.MODEL_IDENTIFIER_TYPEDEF)\r
1681 TdSet = Db.TblFile.Exec(SqlStatement)\r
1682 TdList = []\r
1683 for Td in TdSet:\r
1684 TdList.append(Td)\r
1685 # Check member variable name format that from typedefs of ONLY this file.\r
1686 for Td in TdList:\r
1687 Name = Td[1].strip()\r
1688 Value = Td[2].strip()\r
1689 if Value.startswith('enum'):\r
1690 ValueModelId = DataClass.MODEL_IDENTIFIER_ENUMERATE\r
1691 elif Value.startswith('struct'):\r
1692 ValueModelId = DataClass.MODEL_IDENTIFIER_STRUCTURE\r
1693 elif Value.startswith('union'):\r
1694 ValueModelId = DataClass.MODEL_IDENTIFIER_UNION\r
1695 else:\r
1696 continue\r
52302d4d 1697\r
30fdf114
LG
1698 if ValueModelId != ModelId:\r
1699 continue\r
1700 # Check member variable format.\r
1701 ErrMsgList = CheckMemberVariableFormat(Name, Value, FileTable, Td[5], ModelId)\r
1702 for ErrMsg in ErrMsgList:\r
79b74a03 1703 if EccGlobalData.gException.IsException(ERROR_NAMING_CONVENTION_CHECK_VARIABLE_NAME, Name + '.' + ErrMsg):\r
30fdf114 1704 continue\r
79b74a03 1705 PrintErrorMsg(ERROR_NAMING_CONVENTION_CHECK_VARIABLE_NAME, 'Member variable [%s] NOT follow naming convention.' % (Name + '.' + ErrMsg), FileTable, Td[5])\r
52302d4d 1706\r
30fdf114
LG
1707 # First check in current file to see whether struct/union/enum is typedef-ed.\r
1708 UntypedefedList = []\r
1709 for Result in ResultList:\r
1710 # Check member variable format.\r
1711 Name = Result[0].strip()\r
1712 Value = Result[4].strip()\r
1713 if Value.startswith('enum'):\r
1714 ValueModelId = DataClass.MODEL_IDENTIFIER_ENUMERATE\r
1715 elif Value.startswith('struct'):\r
1716 ValueModelId = DataClass.MODEL_IDENTIFIER_STRUCTURE\r
1717 elif Value.startswith('union'):\r
1718 ValueModelId = DataClass.MODEL_IDENTIFIER_UNION\r
1719 else:\r
1720 continue\r
52302d4d 1721\r
30fdf114
LG
1722 if ValueModelId != ModelId:\r
1723 continue\r
1724 ErrMsgList = CheckMemberVariableFormat(Name, Value, FileTable, Result[3], ModelId)\r
1725 for ErrMsg in ErrMsgList:\r
79b74a03 1726 if EccGlobalData.gException.IsException(ERROR_NAMING_CONVENTION_CHECK_VARIABLE_NAME, Result[0] + '.' + ErrMsg):\r
30fdf114 1727 continue\r
79b74a03 1728 PrintErrorMsg(ERROR_NAMING_CONVENTION_CHECK_VARIABLE_NAME, 'Member variable [%s] NOT follow naming convention.' % (Result[0] + '.' + ErrMsg), FileTable, Result[3])\r
30fdf114
LG
1729 # Check whether it is typedefed.\r
1730 Found = False\r
1731 for Td in TdList:\r
1732 # skip function pointer\r
1733 if len(Td[0]) > 0:\r
1734 continue\r
1735 if Result[1] >= Td[3] and Td[4] >= Result[2]:\r
1736 Found = True\r
1737 if not Td[1].isupper():\r
1738 PrintErrorMsg(ErrorType, 'Typedef should be UPPER case', FileTable, Td[5])\r
1739 if Result[0] in Td[2].split():\r
1740 Found = True\r
1741 if not Td[1].isupper():\r
1742 PrintErrorMsg(ErrorType, 'Typedef should be UPPER case', FileTable, Td[5])\r
1743 if Found:\r
1744 break\r
52302d4d 1745\r
30fdf114
LG
1746 if not Found:\r
1747 UntypedefedList.append(Result)\r
1748 continue\r
52302d4d 1749\r
30fdf114
LG
1750 if len(UntypedefedList) == 0:\r
1751 return\r
52302d4d 1752\r
30fdf114
LG
1753 IncludeFileList = GetAllIncludeFiles(FullFileName)\r
1754 TdList = []\r
1755 for F in IncludeFileList:\r
1756 FileID = GetTableID(F, ErrorMsgList)\r
1757 if FileID < 0:\r
1758 continue\r
52302d4d 1759\r
30fdf114
LG
1760 IncludeFileTable = 'Identifier' + str(FileID)\r
1761 SqlStatement = """ select Modifier, Name, Value, StartLine, EndLine, ID\r
1762 from %s\r
1763 where Model = %d\r
1764 """ % (IncludeFileTable, DataClass.MODEL_IDENTIFIER_TYPEDEF)\r
1765 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1766 TdList.extend(ResultSet)\r
52302d4d 1767\r
30fdf114 1768 for Result in UntypedefedList:\r
52302d4d 1769\r
30fdf114
LG
1770 # Check whether it is typedefed.\r
1771 Found = False\r
1772 for Td in TdList:\r
52302d4d 1773\r
30fdf114
LG
1774 if len(Td[0]) > 0:\r
1775 continue\r
1776 if Result[1] >= Td[3] and Td[4] >= Result[2]:\r
1777 Found = True\r
1778 if not Td[1].isupper():\r
1779 PrintErrorMsg(ErrorType, 'Typedef should be UPPER case', FileTable, Td[5])\r
1780 if Result[0] in Td[2].split():\r
1781 Found = True\r
1782 if not Td[1].isupper():\r
1783 PrintErrorMsg(ErrorType, 'Typedef should be UPPER case', FileTable, Td[5])\r
1784 if Found:\r
1785 break\r
52302d4d 1786\r
30fdf114
LG
1787 if not Found:\r
1788 PrintErrorMsg(ErrorType, 'No Typedef for %s' % Result[0], FileTable, Result[3])\r
1789 continue\r
52302d4d 1790\r
30fdf114
LG
1791def CheckDeclStructTypedef(FullFileName):\r
1792 CheckDeclTypedefFormat(FullFileName, DataClass.MODEL_IDENTIFIER_STRUCTURE)\r
1793\r
1794def CheckDeclEnumTypedef(FullFileName):\r
1795 CheckDeclTypedefFormat(FullFileName, DataClass.MODEL_IDENTIFIER_ENUMERATE)\r
52302d4d 1796\r
30fdf114
LG
1797def CheckDeclUnionTypedef(FullFileName):\r
1798 CheckDeclTypedefFormat(FullFileName, DataClass.MODEL_IDENTIFIER_UNION)\r
1799\r
1800def CheckDeclArgModifier(FullFileName):\r
1801 ErrorMsgList = []\r
52302d4d 1802\r
30fdf114
LG
1803 FileID = GetTableID(FullFileName, ErrorMsgList)\r
1804 if FileID < 0:\r
1805 return ErrorMsgList\r
52302d4d 1806\r
30fdf114
LG
1807 Db = GetDB()\r
1808 FileTable = 'Identifier' + str(FileID)\r
1809 SqlStatement = """ select Modifier, Name, ID\r
1810 from %s\r
1811 where Model = %d\r
1812 """ % (FileTable, DataClass.MODEL_IDENTIFIER_VARIABLE)\r
1813 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1814 ModifierTuple = ('IN', 'OUT', 'OPTIONAL', 'UNALIGNED')\r
1815 MAX_MODIFIER_LENGTH = 100\r
1816 for Result in ResultSet:\r
1817 for Modifier in ModifierTuple:\r
1818 if PatternInModifier(Result[0], Modifier) and len(Result[0]) < MAX_MODIFIER_LENGTH:\r
1819 PrintErrorMsg(ERROR_DECLARATION_DATA_TYPE_CHECK_IN_OUT_MODIFIER, 'Variable Modifier %s' % Result[0], FileTable, Result[2])\r
1820 break\r
52302d4d 1821\r
30fdf114
LG
1822 SqlStatement = """ select Modifier, Name, ID\r
1823 from %s\r
1824 where Model = %d\r
1825 """ % (FileTable, DataClass.MODEL_IDENTIFIER_FUNCTION_DECLARATION)\r
1826 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1827 for Result in ResultSet:\r
1828 for Modifier in ModifierTuple:\r
1829 if PatternInModifier(Result[0], Modifier):\r
1830 PrintErrorMsg(ERROR_DECLARATION_DATA_TYPE_CHECK_IN_OUT_MODIFIER, 'Return Type Modifier %s' % Result[0], FileTable, Result[2])\r
1831 break\r
52302d4d 1832\r
30fdf114
LG
1833 SqlStatement = """ select Modifier, Header, ID\r
1834 from Function\r
1835 where BelongsToFile = %d\r
1836 """ % (FileID)\r
1837 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1838 for Result in ResultSet:\r
1839 for Modifier in ModifierTuple:\r
1840 if PatternInModifier(Result[0], Modifier):\r
1841 PrintErrorMsg(ERROR_DECLARATION_DATA_TYPE_CHECK_IN_OUT_MODIFIER, 'Return Type Modifier %s' % Result[0], FileTable, Result[2])\r
1842 break\r
1843\r
1844def CheckDeclNoUseCType(FullFileName):\r
1845 ErrorMsgList = []\r
52302d4d 1846\r
30fdf114
LG
1847 FileID = GetTableID(FullFileName, ErrorMsgList)\r
1848 if FileID < 0:\r
1849 return ErrorMsgList\r
52302d4d 1850\r
30fdf114
LG
1851 Db = GetDB()\r
1852 FileTable = 'Identifier' + str(FileID)\r
1853 SqlStatement = """ select Modifier, Name, ID\r
1854 from %s\r
1855 where Model = %d\r
1856 """ % (FileTable, DataClass.MODEL_IDENTIFIER_VARIABLE)\r
1857 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1858 CTypeTuple = ('int', 'unsigned', 'char', 'void', 'static', 'long')\r
1859 for Result in ResultSet:\r
1860 for Type in CTypeTuple:\r
1861 if PatternInModifier(Result[0], Type):\r
dbc85eb9
HC
1862 if EccGlobalData.gException.IsException(ERROR_DECLARATION_DATA_TYPE_CHECK_NO_USE_C_TYPE,\r
1863 Result[0] + ' ' + Result[1]):\r
1864 continue\r
1865 PrintErrorMsg(ERROR_DECLARATION_DATA_TYPE_CHECK_NO_USE_C_TYPE,\r
1866 'Invalid variable type (%s) in definition [%s]' % (Type, Result[0] + ' ' + Result[1]),\r
1867 FileTable,\r
1868 Result[2])\r
30fdf114 1869 break\r
52302d4d 1870\r
30fdf114
LG
1871 SqlStatement = """ select Modifier, Name, ID, Value\r
1872 from %s\r
1873 where Model = %d\r
1874 """ % (FileTable, DataClass.MODEL_IDENTIFIER_FUNCTION_DECLARATION)\r
1875 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1876 for Result in ResultSet:\r
1877 ParamList = GetParamList(Result[1])\r
1878 FuncName = Result[3]\r
1879 if EccGlobalData.gException.IsException(ERROR_DECLARATION_DATA_TYPE_CHECK_NO_USE_C_TYPE, FuncName):\r
1880 continue\r
1881 for Type in CTypeTuple:\r
1882 if PatternInModifier(Result[0], Type):\r
1883 PrintErrorMsg(ERROR_DECLARATION_DATA_TYPE_CHECK_NO_USE_C_TYPE, '%s Return type %s' % (FuncName, Result[0]), FileTable, Result[2])\r
52302d4d 1884\r
30fdf114
LG
1885 for Param in ParamList:\r
1886 if PatternInModifier(Param.Modifier, Type):\r
1887 PrintErrorMsg(ERROR_DECLARATION_DATA_TYPE_CHECK_NO_USE_C_TYPE, 'Parameter %s' % Param.Name, FileTable, Result[2])\r
52302d4d 1888\r
30fdf114
LG
1889 SqlStatement = """ select Modifier, Header, ID, Name\r
1890 from Function\r
1891 where BelongsToFile = %d\r
1892 """ % (FileID)\r
1893 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1894 for Result in ResultSet:\r
1895 ParamList = GetParamList(Result[1])\r
1896 FuncName = Result[3]\r
1897 if EccGlobalData.gException.IsException(ERROR_DECLARATION_DATA_TYPE_CHECK_NO_USE_C_TYPE, FuncName):\r
1898 continue\r
1899 for Type in CTypeTuple:\r
1900 if PatternInModifier(Result[0], Type):\r
1901 PrintErrorMsg(ERROR_DECLARATION_DATA_TYPE_CHECK_NO_USE_C_TYPE, '[%s] Return type %s' % (FuncName, Result[0]), FileTable, Result[2])\r
52302d4d 1902\r
30fdf114
LG
1903 for Param in ParamList:\r
1904 if PatternInModifier(Param.Modifier, Type):\r
1905 PrintErrorMsg(ERROR_DECLARATION_DATA_TYPE_CHECK_NO_USE_C_TYPE, 'Parameter %s' % Param.Name, FileTable, Result[2])\r
52302d4d 1906\r
30fdf114
LG
1907\r
1908def CheckPointerNullComparison(FullFileName):\r
1909 ErrorMsgList = []\r
52302d4d 1910\r
30fdf114
LG
1911 FileID = GetTableID(FullFileName, ErrorMsgList)\r
1912 if FileID < 0:\r
1913 return ErrorMsgList\r
52302d4d 1914\r
30fdf114
LG
1915 # cache the found function return type to accelerate later checking in this file.\r
1916 FuncReturnTypeDict = {}\r
52302d4d 1917\r
30fdf114
LG
1918 Db = GetDB()\r
1919 FileTable = 'Identifier' + str(FileID)\r
1920 SqlStatement = """ select Value, StartLine, ID\r
1921 from %s\r
1922 where Model = %d\r
1923 """ % (FileTable, DataClass.MODEL_IDENTIFIER_PREDICATE_EXPRESSION)\r
1924 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1925 if len(ResultSet) == 0:\r
1926 return\r
1927 PSL = []\r
1928 for Result in ResultSet:\r
1929 PSL.append([Result[0], Result[1], Result[2]])\r
52302d4d 1930\r
30fdf114
LG
1931 SqlStatement = """ select BodyStartLine, EndLine, Header, Modifier, ID\r
1932 from Function\r
1933 where BelongsToFile = %d\r
1934 """ % (FileID)\r
1935 ResultSet = Db.TblFile.Exec(SqlStatement)\r
1936 FL = []\r
1937 for Result in ResultSet:\r
1938 FL.append([Result[0], Result[1], Result[2], Result[3], Result[4]])\r
52302d4d 1939\r
30fdf114
LG
1940 p = GetFuncDeclPattern()\r
1941 for Str in PSL:\r
1942 FuncRecord = GetFuncContainsPE(Str[1], FL)\r
4231a819 1943 if FuncRecord is None:\r
30fdf114 1944 continue\r
52302d4d 1945\r
30fdf114
LG
1946 for Exp in GetPredicateListFromPredicateExpStr(Str[0]):\r
1947 PredInfo = SplitPredicateStr(Exp)\r
4231a819 1948 if PredInfo[1] is None:\r
30fdf114
LG
1949 PredVarStr = PredInfo[0][0].strip()\r
1950 IsFuncCall = False\r
1951 SearchInCache = False\r
1952 # PredVarStr may contain '.' or '->'\r
1953 TmpStr = PredVarStr.replace('.', '').replace('->', '')\r
1954 if p.match(TmpStr):\r
1955 PredVarStr = PredVarStr[0:PredVarStr.find('(')]\r
1956 SearchInCache = True\r
1957 # Only direct function call using IsFuncCall branch. Multi-level ref. function call is considered a variable.\r
52302d4d 1958 if TmpStr.startswith(PredVarStr):\r
30fdf114 1959 IsFuncCall = True\r
52302d4d 1960\r
30fdf114
LG
1961 if PredVarStr.strip() in IgnoredKeywordList:\r
1962 continue\r
1963 StarList = []\r
1964 PredVarList = GetCNameList(PredVarStr, StarList)\r
1965 # No variable found, maybe value first? like (0 == VarName)\r
1966 if len(PredVarList) == 0:\r
1967 continue\r
1968 if SearchInCache:\r
1969 Type = FuncReturnTypeDict.get(PredVarStr)\r
4231a819 1970 if Type is not None:\r
79b74a03 1971 if Type.find('*') != -1 and Type != 'BOOLEAN*':\r
30fdf114
LG
1972 PrintErrorMsg(ERROR_PREDICATE_EXPRESSION_CHECK_COMPARISON_NULL_TYPE, 'Predicate Expression: %s' % Exp, FileTable, Str[2])\r
1973 continue\r
52302d4d 1974\r
30fdf114
LG
1975 if PredVarStr in FuncReturnTypeDict:\r
1976 continue\r
52302d4d 1977\r
30fdf114
LG
1978 Type = GetVarInfo(PredVarList, FuncRecord, FullFileName, IsFuncCall, None, StarList)\r
1979 if SearchInCache:\r
1980 FuncReturnTypeDict[PredVarStr] = Type\r
4231a819 1981 if Type is None:\r
30fdf114 1982 continue\r
52302d4d 1983 Type = GetTypeFromArray(Type, PredVarStr)\r
79b74a03 1984 if Type.find('*') != -1 and Type != 'BOOLEAN*':\r
30fdf114
LG
1985 PrintErrorMsg(ERROR_PREDICATE_EXPRESSION_CHECK_COMPARISON_NULL_TYPE, 'Predicate Expression: %s' % Exp, FileTable, Str[2])\r
1986\r
1987def CheckNonBooleanValueComparison(FullFileName):\r
1988 ErrorMsgList = []\r
52302d4d 1989\r
30fdf114
LG
1990 FileID = GetTableID(FullFileName, ErrorMsgList)\r
1991 if FileID < 0:\r
1992 return ErrorMsgList\r
52302d4d 1993\r
30fdf114
LG
1994 # cache the found function return type to accelerate later checking in this file.\r
1995 FuncReturnTypeDict = {}\r
52302d4d 1996\r
30fdf114
LG
1997 Db = GetDB()\r
1998 FileTable = 'Identifier' + str(FileID)\r
1999 SqlStatement = """ select Value, StartLine, ID\r
2000 from %s\r
2001 where Model = %d\r
2002 """ % (FileTable, DataClass.MODEL_IDENTIFIER_PREDICATE_EXPRESSION)\r
2003 ResultSet = Db.TblFile.Exec(SqlStatement)\r
2004 if len(ResultSet) == 0:\r
2005 return\r
2006 PSL = []\r
2007 for Result in ResultSet:\r
2008 PSL.append([Result[0], Result[1], Result[2]])\r
52302d4d 2009\r
30fdf114
LG
2010 SqlStatement = """ select BodyStartLine, EndLine, Header, Modifier, ID\r
2011 from Function\r
2012 where BelongsToFile = %d\r
2013 """ % (FileID)\r
2014 ResultSet = Db.TblFile.Exec(SqlStatement)\r
2015 FL = []\r
2016 for Result in ResultSet:\r
2017 FL.append([Result[0], Result[1], Result[2], Result[3], Result[4]])\r
52302d4d 2018\r
30fdf114
LG
2019 p = GetFuncDeclPattern()\r
2020 for Str in PSL:\r
2021 FuncRecord = GetFuncContainsPE(Str[1], FL)\r
4231a819 2022 if FuncRecord is None:\r
30fdf114 2023 continue\r
52302d4d 2024\r
30fdf114 2025 for Exp in GetPredicateListFromPredicateExpStr(Str[0]):\r
30fdf114 2026 PredInfo = SplitPredicateStr(Exp)\r
4231a819 2027 if PredInfo[1] is None:\r
30fdf114
LG
2028 PredVarStr = PredInfo[0][0].strip()\r
2029 IsFuncCall = False\r
2030 SearchInCache = False\r
2031 # PredVarStr may contain '.' or '->'\r
2032 TmpStr = PredVarStr.replace('.', '').replace('->', '')\r
2033 if p.match(TmpStr):\r
2034 PredVarStr = PredVarStr[0:PredVarStr.find('(')]\r
2035 SearchInCache = True\r
2036 # Only direct function call using IsFuncCall branch. Multi-level ref. function call is considered a variable.\r
52302d4d 2037 if TmpStr.startswith(PredVarStr):\r
30fdf114 2038 IsFuncCall = True\r
52302d4d 2039\r
30fdf114
LG
2040 if PredVarStr.strip() in IgnoredKeywordList:\r
2041 continue\r
2042 StarList = []\r
2043 PredVarList = GetCNameList(PredVarStr, StarList)\r
2044 # No variable found, maybe value first? like (0 == VarName)\r
2045 if len(PredVarList) == 0:\r
2046 continue\r
52302d4d 2047\r
30fdf114
LG
2048 if SearchInCache:\r
2049 Type = FuncReturnTypeDict.get(PredVarStr)\r
4231a819 2050 if Type is not None:\r
30fdf114
LG
2051 if Type.find('BOOLEAN') == -1:\r
2052 PrintErrorMsg(ERROR_PREDICATE_EXPRESSION_CHECK_NO_BOOLEAN_OPERATOR, 'Predicate Expression: %s' % Exp, FileTable, Str[2])\r
2053 continue\r
52302d4d 2054\r
30fdf114
LG
2055 if PredVarStr in FuncReturnTypeDict:\r
2056 continue\r
30fdf114
LG
2057 Type = GetVarInfo(PredVarList, FuncRecord, FullFileName, IsFuncCall, 'BOOLEAN', StarList)\r
2058 if SearchInCache:\r
2059 FuncReturnTypeDict[PredVarStr] = Type\r
4231a819 2060 if Type is None:\r
30fdf114
LG
2061 continue\r
2062 if Type.find('BOOLEAN') == -1:\r
2063 PrintErrorMsg(ERROR_PREDICATE_EXPRESSION_CHECK_NO_BOOLEAN_OPERATOR, 'Predicate Expression: %s' % Exp, FileTable, Str[2])\r
52302d4d 2064\r
30fdf114
LG
2065\r
2066def CheckBooleanValueComparison(FullFileName):\r
2067 ErrorMsgList = []\r
52302d4d 2068\r
30fdf114
LG
2069 FileID = GetTableID(FullFileName, ErrorMsgList)\r
2070 if FileID < 0:\r
2071 return ErrorMsgList\r
52302d4d 2072\r
30fdf114
LG
2073 # cache the found function return type to accelerate later checking in this file.\r
2074 FuncReturnTypeDict = {}\r
52302d4d 2075\r
30fdf114
LG
2076 Db = GetDB()\r
2077 FileTable = 'Identifier' + str(FileID)\r
2078 SqlStatement = """ select Value, StartLine, ID\r
2079 from %s\r
2080 where Model = %d\r
2081 """ % (FileTable, DataClass.MODEL_IDENTIFIER_PREDICATE_EXPRESSION)\r
2082 ResultSet = Db.TblFile.Exec(SqlStatement)\r
2083 if len(ResultSet) == 0:\r
2084 return\r
2085 PSL = []\r
2086 for Result in ResultSet:\r
2087 PSL.append([Result[0], Result[1], Result[2]])\r
52302d4d 2088\r
30fdf114
LG
2089 SqlStatement = """ select BodyStartLine, EndLine, Header, Modifier, ID\r
2090 from Function\r
2091 where BelongsToFile = %d\r
2092 """ % (FileID)\r
2093 ResultSet = Db.TblFile.Exec(SqlStatement)\r
2094 FL = []\r
2095 for Result in ResultSet:\r
2096 FL.append([Result[0], Result[1], Result[2], Result[3], Result[4]])\r
52302d4d 2097\r
30fdf114
LG
2098 p = GetFuncDeclPattern()\r
2099 for Str in PSL:\r
2100 FuncRecord = GetFuncContainsPE(Str[1], FL)\r
4231a819 2101 if FuncRecord is None:\r
30fdf114 2102 continue\r
52302d4d 2103\r
30fdf114
LG
2104 for Exp in GetPredicateListFromPredicateExpStr(Str[0]):\r
2105 PredInfo = SplitPredicateStr(Exp)\r
2106 if PredInfo[1] in ('==', '!=') and PredInfo[0][1] in ('TRUE', 'FALSE'):\r
2107 PredVarStr = PredInfo[0][0].strip()\r
2108 IsFuncCall = False\r
2109 SearchInCache = False\r
2110 # PredVarStr may contain '.' or '->'\r
2111 TmpStr = PredVarStr.replace('.', '').replace('->', '')\r
2112 if p.match(TmpStr):\r
2113 PredVarStr = PredVarStr[0:PredVarStr.find('(')]\r
2114 SearchInCache = True\r
2115 # Only direct function call using IsFuncCall branch. Multi-level ref. function call is considered a variable.\r
52302d4d 2116 if TmpStr.startswith(PredVarStr):\r
30fdf114 2117 IsFuncCall = True\r
52302d4d 2118\r
30fdf114
LG
2119 if PredVarStr.strip() in IgnoredKeywordList:\r
2120 continue\r
2121 StarList = []\r
2122 PredVarList = GetCNameList(PredVarStr, StarList)\r
2123 # No variable found, maybe value first? like (0 == VarName)\r
2124 if len(PredVarList) == 0:\r
2125 continue\r
52302d4d 2126\r
30fdf114
LG
2127 if SearchInCache:\r
2128 Type = FuncReturnTypeDict.get(PredVarStr)\r
4231a819 2129 if Type is not None:\r
30fdf114
LG
2130 if Type.find('BOOLEAN') != -1:\r
2131 PrintErrorMsg(ERROR_PREDICATE_EXPRESSION_CHECK_BOOLEAN_VALUE, 'Predicate Expression: %s' % Exp, FileTable, Str[2])\r
2132 continue\r
52302d4d 2133\r
30fdf114
LG
2134 if PredVarStr in FuncReturnTypeDict:\r
2135 continue\r
52302d4d 2136\r
30fdf114
LG
2137 Type = GetVarInfo(PredVarList, FuncRecord, FullFileName, IsFuncCall, 'BOOLEAN', StarList)\r
2138 if SearchInCache:\r
2139 FuncReturnTypeDict[PredVarStr] = Type\r
4231a819 2140 if Type is None:\r
30fdf114
LG
2141 continue\r
2142 if Type.find('BOOLEAN') != -1:\r
2143 PrintErrorMsg(ERROR_PREDICATE_EXPRESSION_CHECK_BOOLEAN_VALUE, 'Predicate Expression: %s' % Exp, FileTable, Str[2])\r
52302d4d 2144\r
30fdf114
LG
2145\r
2146def CheckHeaderFileData(FullFileName):\r
2147 ErrorMsgList = []\r
52302d4d 2148\r
30fdf114
LG
2149 FileID = GetTableID(FullFileName, ErrorMsgList)\r
2150 if FileID < 0:\r
2151 return ErrorMsgList\r
52302d4d 2152\r
30fdf114
LG
2153 Db = GetDB()\r
2154 FileTable = 'Identifier' + str(FileID)\r
2155 SqlStatement = """ select ID, Modifier\r
2156 from %s\r
2157 where Model = %d\r
2158 """ % (FileTable, DataClass.MODEL_IDENTIFIER_VARIABLE)\r
2159 ResultSet = Db.TblFile.Exec(SqlStatement)\r
2160 for Result in ResultSet:\r
2161 if not Result[1].startswith('extern'):\r
2162 PrintErrorMsg(ERROR_INCLUDE_FILE_CHECK_DATA, 'Variable definition appears in header file', FileTable, Result[0])\r
52302d4d 2163\r
30fdf114
LG
2164 SqlStatement = """ select ID\r
2165 from Function\r
2166 where BelongsToFile = %d\r
2167 """ % FileID\r
2168 ResultSet = Db.TblFile.Exec(SqlStatement)\r
2169 for Result in ResultSet:\r
2170 PrintErrorMsg(ERROR_INCLUDE_FILE_CHECK_DATA, 'Function definition appears in header file', 'Function', Result[0])\r
2171\r
2172 return ErrorMsgList\r
2173\r
2174def CheckHeaderFileIfndef(FullFileName):\r
2175 ErrorMsgList = []\r
52302d4d 2176\r
30fdf114
LG
2177 FileID = GetTableID(FullFileName, ErrorMsgList)\r
2178 if FileID < 0:\r
2179 return ErrorMsgList\r
52302d4d 2180\r
30fdf114
LG
2181 Db = GetDB()\r
2182 FileTable = 'Identifier' + str(FileID)\r
2183 SqlStatement = """ select Value, StartLine\r
2184 from %s\r
2185 where Model = %d order by StartLine\r
2186 """ % (FileTable, DataClass.MODEL_IDENTIFIER_MACRO_IFNDEF)\r
2187 ResultSet = Db.TblFile.Exec(SqlStatement)\r
2188 if len(ResultSet) == 0:\r
2189 PrintErrorMsg(ERROR_INCLUDE_FILE_CHECK_IFNDEF_STATEMENT_1, '', 'File', FileID)\r
2190 return ErrorMsgList\r
2191 for Result in ResultSet:\r
2192 SqlStatement = """ select Value, EndLine\r
2193 from %s\r
2194 where EndLine < %d\r
2195 """ % (FileTable, Result[1])\r
2196 ResultSet = Db.TblFile.Exec(SqlStatement)\r
2197 for Result in ResultSet:\r
2198 if not Result[0].startswith('/*') and not Result[0].startswith('//'):\r
2199 PrintErrorMsg(ERROR_INCLUDE_FILE_CHECK_IFNDEF_STATEMENT_2, '', 'File', FileID)\r
2200 break\r
52302d4d 2201\r
30fdf114
LG
2202 SqlStatement = """ select Value\r
2203 from %s\r
2204 where StartLine > (select max(EndLine) from %s where Model = %d)\r
2205 """ % (FileTable, FileTable, DataClass.MODEL_IDENTIFIER_MACRO_ENDIF)\r
2206 ResultSet = Db.TblFile.Exec(SqlStatement)\r
2207 for Result in ResultSet:\r
2208 if not Result[0].startswith('/*') and not Result[0].startswith('//'):\r
2209 PrintErrorMsg(ERROR_INCLUDE_FILE_CHECK_IFNDEF_STATEMENT_3, '', 'File', FileID)\r
2210 return ErrorMsgList\r
2211\r
2212def CheckDoxygenCommand(FullFileName):\r
2213 ErrorMsgList = []\r
52302d4d 2214\r
30fdf114
LG
2215 FileID = GetTableID(FullFileName, ErrorMsgList)\r
2216 if FileID < 0:\r
2217 return ErrorMsgList\r
52302d4d 2218\r
30fdf114
LG
2219 Db = GetDB()\r
2220 FileTable = 'Identifier' + str(FileID)\r
2221 SqlStatement = """ select Value, ID\r
2222 from %s\r
2223 where Model = %d or Model = %d\r
2224 """ % (FileTable, DataClass.MODEL_IDENTIFIER_COMMENT, DataClass.MODEL_IDENTIFIER_FUNCTION_HEADER)\r
2225 ResultSet = Db.TblFile.Exec(SqlStatement)\r
f8895c2a
HC
2226 DoxygenCommandList = ['bug', 'todo', 'example', 'file', 'attention', 'param', 'post', 'pre', 'retval',\r
2227 'return', 'sa', 'since', 'test', 'note', 'par', 'endcode', 'code']\r
30fdf114
LG
2228 for Result in ResultSet:\r
2229 CommentStr = Result[0]\r
2230 CommentPartList = CommentStr.split()\r
2231 for Part in CommentPartList:\r
2232 if Part.upper() == 'BUGBUG':\r
2233 PrintErrorMsg(ERROR_DOXYGEN_CHECK_COMMAND, 'Bug should be marked with doxygen tag @bug', FileTable, Result[1])\r
2234 if Part.upper() == 'TODO':\r
2235 PrintErrorMsg(ERROR_DOXYGEN_CHECK_COMMAND, 'ToDo should be marked with doxygen tag @todo', FileTable, Result[1])\r
2236 if Part.startswith('@'):\r
2237 if EccGlobalData.gException.IsException(ERROR_DOXYGEN_CHECK_COMMAND, Part):\r
2238 continue\r
f8895c2a
HC
2239 if not Part.replace('@', '').strip():\r
2240 continue\r
2241 if Part.lstrip('@') in ['{', '}']:\r
2242 continue\r
30fdf114
LG
2243 if Part.lstrip('@').isalpha():\r
2244 if Part.lstrip('@') not in DoxygenCommandList:\r
2245 PrintErrorMsg(ERROR_DOXYGEN_CHECK_COMMAND, 'Unknown doxygen command %s' % Part, FileTable, Result[1])\r
2246 else:\r
2247 Index = Part.find('[')\r
2248 if Index == -1:\r
2249 PrintErrorMsg(ERROR_DOXYGEN_CHECK_COMMAND, 'Unknown doxygen command %s' % Part, FileTable, Result[1])\r
2250 RealCmd = Part[1:Index]\r
2251 if RealCmd not in DoxygenCommandList:\r
2252 PrintErrorMsg(ERROR_DOXYGEN_CHECK_COMMAND, 'Unknown doxygen command %s' % Part, FileTable, Result[1])\r
52302d4d
LG
2253\r
2254\r
30fdf114
LG
2255def CheckDoxygenTripleForwardSlash(FullFileName):\r
2256 ErrorMsgList = []\r
52302d4d 2257\r
30fdf114
LG
2258 FileID = GetTableID(FullFileName, ErrorMsgList)\r
2259 if FileID < 0:\r
2260 return ErrorMsgList\r
52302d4d 2261\r
30fdf114 2262 Db = GetDB()\r
52302d4d 2263\r
30fdf114
LG
2264 SqlStatement = """ select ID, BodyStartLine, BodyStartColumn, EndLine, EndColumn\r
2265 from Function\r
2266 where BelongsToFile = %d\r
2267 """ % (FileID)\r
2268 ResultSet = Db.TblFile.Exec(SqlStatement)\r
2269 if len(ResultSet) == 0:\r
2270 return\r
52302d4d
LG
2271\r
2272 FuncDefSet = []\r
30fdf114
LG
2273 for Result in ResultSet:\r
2274 FuncDefSet.append(Result)\r
52302d4d
LG
2275\r
2276\r
30fdf114
LG
2277 FileTable = 'Identifier' + str(FileID)\r
2278 SqlStatement = """ select Value, ID, StartLine, StartColumn, EndLine, EndColumn\r
2279 from %s\r
52302d4d
LG
2280 where Model = %d\r
2281\r
30fdf114
LG
2282 """ % (FileTable, DataClass.MODEL_IDENTIFIER_COMMENT)\r
2283 ResultSet = Db.TblFile.Exec(SqlStatement)\r
2284 CommentSet = []\r
2285 try:\r
2286 for Result in ResultSet:\r
2287 CommentSet.append(Result)\r
2288 except:\r
72443dd2 2289 print('Unrecognized chars in comment of file %s', FullFileName)\r
52302d4d
LG
2290\r
2291\r
30fdf114
LG
2292 for Result in CommentSet:\r
2293 CommentStr = Result[0]\r
2294 StartLine = Result[2]\r
2295 StartColumn = Result[3]\r
2296 EndLine = Result[4]\r
2297 EndColumn = Result[5]\r
2298 if not CommentStr.startswith('///<'):\r
2299 continue\r
52302d4d 2300\r
30fdf114
LG
2301 Found = False\r
2302 for FuncDef in FuncDefSet:\r
2303 if StartLine == FuncDef[1] and StartColumn > FuncDef[2] and EndLine == FuncDef[3] and EndColumn < FuncDef[4]:\r
2304 Found = True\r
2305 break\r
2306 if StartLine > FuncDef[1] and EndLine < FuncDef[3]:\r
2307 Found = True\r
2308 break\r
2309 if StartLine == FuncDef[1] and StartColumn > FuncDef[2] and EndLine < FuncDef[3]:\r
2310 Found = True\r
2311 break\r
2312 if StartLine > FuncDef[1] and EndLine == FuncDef[3] and EndColumn < FuncDef[4]:\r
2313 Found = True\r
2314 break\r
2315 if Found:\r
2316 PrintErrorMsg(ERROR_DOXYGEN_CHECK_COMMENT_FORMAT, '', FileTable, Result[1])\r
2317\r
2318\r
2319def CheckFileHeaderDoxygenComments(FullFileName):\r
2320 ErrorMsgList = []\r
52302d4d 2321\r
30fdf114
LG
2322 FileID = GetTableID(FullFileName, ErrorMsgList)\r
2323 if FileID < 0:\r
2324 return ErrorMsgList\r
52302d4d 2325\r
30fdf114
LG
2326 Db = GetDB()\r
2327 FileTable = 'Identifier' + str(FileID)\r
2328 SqlStatement = """ select Value, ID\r
2329 from %s\r
e56468c0 2330 where Model = %d and (StartLine = 1 or StartLine = 7 or StartLine = 8) and StartColumn = 0\r
30fdf114
LG
2331 """ % (FileTable, DataClass.MODEL_IDENTIFIER_COMMENT)\r
2332 ResultSet = Db.TblFile.Exec(SqlStatement)\r
2333 if len(ResultSet) == 0:\r
d0acc87a 2334 PrintErrorMsg(ERROR_HEADER_CHECK_FILE, 'No File License header appear at the very beginning of file.', 'File', FileID)\r
30fdf114 2335 return ErrorMsgList\r
52302d4d 2336\r
d0acc87a
LG
2337 NoHeaderCommentStartFlag = True\r
2338 NoHeaderCommentEndFlag = True\r
2339 NoHeaderCommentPeriodFlag = True\r
2340 NoCopyrightFlag = True\r
2341 NoLicenseFlag = True\r
2342 NoRevReferFlag = True\r
2343 NextLineIndex = 0\r
30fdf114 2344 for Result in ResultSet:\r
d0acc87a
LG
2345 FileStartFlag = False\r
2346 CommentStrList = []\r
e56468c0 2347 CommentStr = Result[0].strip()\r
d0acc87a
LG
2348 CommentStrListTemp = CommentStr.split('\n')\r
2349 if (len(CommentStrListTemp) <= 1):\r
2350 # For Mac\r
2351 CommentStrListTemp = CommentStr.split('\r')\r
2352 # Skip the content before the file header \r
2353 for CommentLine in CommentStrListTemp:\r
2354 if CommentLine.strip().startswith('/** @file'):\r
2355 FileStartFlag = True\r
2356 if FileStartFlag == True:\r
2357 CommentStrList.append(CommentLine)\r
2358 \r
e56468c0 2359 ID = Result[1]\r
d0acc87a
LG
2360 Index = 0\r
2361 if CommentStrList and CommentStrList[0].strip().startswith('/** @file'):\r
2362 NoHeaderCommentStartFlag = False\r
2363 else:\r
2364 continue\r
2365 if CommentStrList and CommentStrList[-1].strip().endswith('**/'):\r
2366 NoHeaderCommentEndFlag = False\r
2367 else:\r
2368 continue\r
2369\r
2370 for CommentLine in CommentStrList:\r
2371 Index = Index + 1\r
2372 NextLineIndex = Index\r
2373 if CommentLine.startswith('/** @file'):\r
2374 continue\r
2375 if CommentLine.startswith('**/'):\r
2376 break\r
2377 # Check whether C File header Comment content start with two spaces.\r
2378 if EccGlobalData.gConfig.HeaderCheckCFileCommentStartSpacesNum == '1' or EccGlobalData.gConfig.HeaderCheckAll == '1' or EccGlobalData.gConfig.CheckAll == '1':\r
2379 if CommentLine.startswith('/** @file') == False and CommentLine.startswith('**/') == False and CommentLine.strip() and CommentLine.startswith(' ') == False:\r
2380 PrintErrorMsg(ERROR_HEADER_CHECK_FILE, 'File header comment content should start with two spaces at each line', FileTable, ID)\r
2381 \r
2382 CommentLine = CommentLine.strip()\r
2383 if CommentLine.startswith('Copyright'):\r
2384 NoCopyrightFlag = False\r
2385 if CommentLine.find('All rights reserved') == -1:\r
d77cc206
HC
2386 for Copyright in EccGlobalData.gConfig.Copyright:\r
2387 if CommentLine.find(Copyright) > -1:\r
2388 PrintErrorMsg(ERROR_HEADER_CHECK_FILE, '""All rights reserved"" announcement should be following the ""Copyright"" at the same line', FileTable, ID)\r
2389 break\r
d0acc87a
LG
2390 if CommentLine.endswith('<BR>') == -1:\r
2391 PrintErrorMsg(ERROR_HEADER_CHECK_FILE, 'The ""<BR>"" at the end of the Copyright line is required', FileTable, ID)\r
2392 if NextLineIndex < len(CommentStrList) and CommentStrList[NextLineIndex].strip().startswith('Copyright') == False and CommentStrList[NextLineIndex].strip():\r
2393 NoLicenseFlag = False\r
2394 if CommentLine.startswith('@par Revision Reference:'):\r
2395 NoRevReferFlag = False\r
2396 RefListFlag = False\r
2397 for RefLine in CommentStrList[NextLineIndex:]:\r
2398 if RefLine.strip() and (NextLineIndex + 1) < len(CommentStrList) and CommentStrList[NextLineIndex+1].strip() and CommentStrList[NextLineIndex+1].strip().startswith('**/') == False:\r
2399 RefListFlag = True\r
2400 if RefLine.strip() == False or RefLine.strip().startswith('**/'):\r
2401 RefListFlag = False\r
2402 break\r
2403 # Check whether C File header Comment's each reference at list should begin with a bullet character.\r
2404 if EccGlobalData.gConfig.HeaderCheckCFileCommentReferenceFormat == '1' or EccGlobalData.gConfig.HeaderCheckAll == '1' or EccGlobalData.gConfig.CheckAll == '1':\r
2405 if RefListFlag == True:\r
2406 if RefLine.strip() and RefLine.strip().startswith('**/') == False and RefLine.startswith(' -') == False: \r
2407 PrintErrorMsg(ERROR_HEADER_CHECK_FILE, 'Each reference on a separate line should begin with a bullet character ""-"" ', FileTable, ID) \r
2408 \r
2409 if NoHeaderCommentStartFlag:\r
e56468c0 2410 PrintErrorMsg(ERROR_DOXYGEN_CHECK_FILE_HEADER, 'File header comment should begin with ""/** @file""', FileTable, ID)\r
d0acc87a
LG
2411 return\r
2412 if NoHeaderCommentEndFlag:\r
e56468c0 2413 PrintErrorMsg(ERROR_HEADER_CHECK_FILE, 'File header comment should end with ""**/""', FileTable, ID)\r
d0acc87a
LG
2414 return\r
2415 if NoCopyrightFlag:\r
2416 PrintErrorMsg(ERROR_HEADER_CHECK_FILE, 'File header comment missing the ""Copyright""', FileTable, ID)\r
2417 #Check whether C File header Comment have the License immediately after the ""Copyright"" line.\r
2418 if EccGlobalData.gConfig.HeaderCheckCFileCommentLicenseFormat == '1' or EccGlobalData.gConfig.HeaderCheckAll == '1' or EccGlobalData.gConfig.CheckAll == '1':\r
2419 if NoLicenseFlag:\r
2420 PrintErrorMsg(ERROR_HEADER_CHECK_FILE, 'File header comment should have the License immediately after the ""Copyright"" line', FileTable, ID)\r
30fdf114
LG
2421\r
2422def CheckFuncHeaderDoxygenComments(FullFileName):\r
2423 ErrorMsgList = []\r
52302d4d 2424\r
30fdf114
LG
2425 FileID = GetTableID(FullFileName, ErrorMsgList)\r
2426 if FileID < 0:\r
2427 return ErrorMsgList\r
52302d4d 2428\r
30fdf114
LG
2429 Db = GetDB()\r
2430 FileTable = 'Identifier' + str(FileID)\r
2431 SqlStatement = """ select Value, StartLine, EndLine, ID\r
2432 from %s\r
2433 where Model = %d\r
2434 """ % (FileTable, DataClass.MODEL_IDENTIFIER_COMMENT)\r
52302d4d 2435\r
30fdf114
LG
2436 ResultSet = Db.TblFile.Exec(SqlStatement)\r
2437 CommentSet = []\r
2438 try:\r
2439 for Result in ResultSet:\r
2440 CommentSet.append(Result)\r
2441 except:\r
72443dd2 2442 print('Unrecognized chars in comment of file %s', FullFileName)\r
52302d4d 2443\r
30fdf114
LG
2444 # Func Decl check\r
2445 SqlStatement = """ select Modifier, Name, StartLine, ID, Value\r
2446 from %s\r
2447 where Model = %d\r
2448 """ % (FileTable, DataClass.MODEL_IDENTIFIER_FUNCTION_DECLARATION)\r
2449 ResultSet = Db.TblFile.Exec(SqlStatement)\r
2450 for Result in ResultSet:\r
2451 FuncName = Result[4]\r
2452 FunctionHeaderComment = CheckCommentImmediatelyPrecedeFunctionHeader(Result[1], Result[2], CommentSet)\r
2453 if FunctionHeaderComment:\r
2454 CheckFunctionHeaderConsistentWithDoxygenComment(Result[0], Result[1], Result[2], FunctionHeaderComment[0], FunctionHeaderComment[1], ErrorMsgList, FunctionHeaderComment[3], FileTable)\r
2455 else:\r
2456 if EccGlobalData.gException.IsException(ERROR_HEADER_CHECK_FUNCTION, FuncName):\r
2457 continue\r
2458 ErrorMsgList.append('Line %d :Function %s has NO comment immediately preceding it.' % (Result[2], Result[1]))\r
2459 PrintErrorMsg(ERROR_HEADER_CHECK_FUNCTION, 'Function [%s] has NO comment immediately preceding it.' % (FuncName), FileTable, Result[3])\r
52302d4d 2460\r
30fdf114
LG
2461 # Func Def check\r
2462 SqlStatement = """ select Value, StartLine, EndLine, ID\r
2463 from %s\r
2464 where Model = %d\r
2465 """ % (FileTable, DataClass.MODEL_IDENTIFIER_FUNCTION_HEADER)\r
52302d4d 2466\r
30fdf114
LG
2467 ResultSet = Db.TblFile.Exec(SqlStatement)\r
2468 CommentSet = []\r
2469 try:\r
2470 for Result in ResultSet:\r
2471 CommentSet.append(Result)\r
2472 except:\r
72443dd2 2473 print('Unrecognized chars in comment of file %s', FullFileName)\r
52302d4d 2474\r
30fdf114
LG
2475 SqlStatement = """ select Modifier, Header, StartLine, ID, Name\r
2476 from Function\r
2477 where BelongsToFile = %d\r
2478 """ % (FileID)\r
2479 ResultSet = Db.TblFile.Exec(SqlStatement)\r
2480 for Result in ResultSet:\r
2481 FuncName = Result[4]\r
2482 FunctionHeaderComment = CheckCommentImmediatelyPrecedeFunctionHeader(Result[1], Result[2], CommentSet)\r
2483 if FunctionHeaderComment:\r
2484 CheckFunctionHeaderConsistentWithDoxygenComment(Result[0], Result[1], Result[2], FunctionHeaderComment[0], FunctionHeaderComment[1], ErrorMsgList, FunctionHeaderComment[3], FileTable)\r
2485 else:\r
2486 if EccGlobalData.gException.IsException(ERROR_HEADER_CHECK_FUNCTION, FuncName):\r
2487 continue\r
2488 ErrorMsgList.append('Line %d :Function [%s] has NO comment immediately preceding it.' % (Result[2], Result[1]))\r
2489 PrintErrorMsg(ERROR_HEADER_CHECK_FUNCTION, 'Function [%s] has NO comment immediately preceding it.' % (FuncName), 'Function', Result[3])\r
2490 return ErrorMsgList\r
2491\r
2492def CheckCommentImmediatelyPrecedeFunctionHeader(FuncName, FuncStartLine, CommentSet):\r
2493\r
2494 for Comment in CommentSet:\r
2495 if Comment[2] == FuncStartLine - 1:\r
2496 return Comment\r
2497 return None\r
2498\r
2499def GetDoxygenStrFromComment(Str):\r
2500 DoxygenStrList = []\r
2501 ParamTagList = Str.split('@param')\r
2502 if len(ParamTagList) > 1:\r
2503 i = 1\r
2504 while i < len(ParamTagList):\r
2505 DoxygenStrList.append('@param' + ParamTagList[i])\r
2506 i += 1\r
52302d4d 2507\r
30fdf114 2508 Str = ParamTagList[0]\r
52302d4d 2509\r
30fdf114
LG
2510 RetvalTagList = ParamTagList[-1].split('@retval')\r
2511 if len(RetvalTagList) > 1:\r
2512 if len(ParamTagList) > 1:\r
2513 DoxygenStrList[-1] = '@param' + RetvalTagList[0]\r
2514 i = 1\r
2515 while i < len(RetvalTagList):\r
2516 DoxygenStrList.append('@retval' + RetvalTagList[i])\r
2517 i += 1\r
52302d4d 2518\r
30fdf114
LG
2519 ReturnTagList = RetvalTagList[-1].split('@return')\r
2520 if len(ReturnTagList) > 1:\r
2521 if len(RetvalTagList) > 1:\r
2522 DoxygenStrList[-1] = '@retval' + ReturnTagList[0]\r
2523 elif len(ParamTagList) > 1:\r
2524 DoxygenStrList[-1] = '@param' + ReturnTagList[0]\r
2525 i = 1\r
2526 while i < len(ReturnTagList):\r
2527 DoxygenStrList.append('@return' + ReturnTagList[i])\r
2528 i += 1\r
52302d4d 2529\r
30fdf114
LG
2530 if len(DoxygenStrList) > 0:\r
2531 DoxygenStrList[-1] = DoxygenStrList[-1].rstrip('--*/')\r
52302d4d 2532\r
30fdf114 2533 return DoxygenStrList\r
52302d4d 2534\r
79b74a03 2535def CheckGeneralDoxygenCommentLayout(Str, StartLine, ErrorMsgList, CommentId= -1, TableName=''):\r
30fdf114
LG
2536 #/** --*/ @retval after @param\r
2537 if not Str.startswith('/**'):\r
2538 ErrorMsgList.append('Line %d : Comment does NOT have prefix /** ' % StartLine)\r
2539 PrintErrorMsg(ERROR_DOXYGEN_CHECK_FUNCTION_HEADER, 'Comment does NOT have prefix /** ', TableName, CommentId)\r
2540 if not Str.endswith('**/'):\r
2541 ErrorMsgList.append('Line %d : Comment does NOT have tail **/ ' % StartLine)\r
2542 PrintErrorMsg(ERROR_DOXYGEN_CHECK_FUNCTION_HEADER, 'Comment does NOT have tail **/ ', TableName, CommentId)\r
2543 FirstRetvalIndex = Str.find('@retval')\r
2544 LastParamIndex = Str.rfind('@param')\r
2545 if (FirstRetvalIndex > 0) and (LastParamIndex > 0) and (FirstRetvalIndex < LastParamIndex):\r
2546 ErrorMsgList.append('Line %d : @retval appear before @param ' % StartLine)\r
2547 PrintErrorMsg(ERROR_DOXYGEN_CHECK_FUNCTION_HEADER, 'in Comment, @retval appear before @param ', TableName, CommentId)\r
52302d4d 2548\r
79b74a03 2549def CheckFunctionHeaderConsistentWithDoxygenComment(FuncModifier, FuncHeader, FuncStartLine, CommentStr, CommentStartLine, ErrorMsgList, CommentId= -1, TableName=''):\r
52302d4d
LG
2550\r
2551 ParamList = GetParamList(FuncHeader)\r
30fdf114
LG
2552 CheckGeneralDoxygenCommentLayout(CommentStr, CommentStartLine, ErrorMsgList, CommentId, TableName)\r
2553 DescriptionStr = CommentStr\r
2554 DoxygenStrList = GetDoxygenStrFromComment(DescriptionStr)\r
2555 if DescriptionStr.find('.') == -1:\r
2556 PrintErrorMsg(ERROR_DOXYGEN_CHECK_COMMENT_DESCRIPTION, 'Comment description should end with period \'.\'', TableName, CommentId)\r
2557 DoxygenTagNumber = len(DoxygenStrList)\r
2558 ParamNumber = len(ParamList)\r
2559 for Param in ParamList:\r
2560 if Param.Name.upper() == 'VOID' and ParamNumber == 1:\r
2561 ParamNumber -= 1\r
2562 Index = 0\r
2563 if ParamNumber > 0 and DoxygenTagNumber > 0:\r
2564 while Index < ParamNumber and Index < DoxygenTagNumber:\r
2565 ParamModifier = ParamList[Index].Modifier\r
2566 ParamName = ParamList[Index].Name.strip()\r
2567 Tag = DoxygenStrList[Index].strip(' ')\r
2568 if (not Tag[-1] == ('\n')) and (not Tag[-1] == ('\r')):\r
79b74a03
LG
2569 ErrorMsgList.append('Line %d : in Comment, <%s> does NOT end with new line ' % (CommentStartLine, Tag.replace('\n', '').replace('\r', '')))\r
2570 PrintErrorMsg(ERROR_HEADER_CHECK_FUNCTION, 'in Comment, <%s> does NOT end with new line ' % (Tag.replace('\n', '').replace('\r', '')), TableName, CommentId)\r
30fdf114
LG
2571 TagPartList = Tag.split()\r
2572 if len(TagPartList) < 2:\r
79b74a03
LG
2573 ErrorMsgList.append('Line %d : in Comment, <%s> does NOT contain doxygen contents ' % (CommentStartLine, Tag.replace('\n', '').replace('\r', '')))\r
2574 PrintErrorMsg(ERROR_DOXYGEN_CHECK_FUNCTION_HEADER, 'in Comment, <%s> does NOT contain doxygen contents ' % (Tag.replace('\n', '').replace('\r', '')), TableName, CommentId)\r
30fdf114
LG
2575 Index += 1\r
2576 continue\r
2577 LBPos = Tag.find('[')\r
2578 RBPos = Tag.find(']')\r
2579 ParamToLBContent = Tag[len('@param'):LBPos].strip()\r
79b74a03 2580 if LBPos > 0 and len(ParamToLBContent) == 0 and RBPos > LBPos:\r
30fdf114
LG
2581 InOutStr = ''\r
2582 ModifierPartList = ParamModifier.split()\r
2583 for Part in ModifierPartList:\r
2584 if Part.strip() == 'IN':\r
2585 InOutStr += 'in'\r
2586 if Part.strip() == 'OUT':\r
52302d4d 2587 if InOutStr != '':\r
30fdf114
LG
2588 InOutStr += ', out'\r
2589 else:\r
2590 InOutStr = 'out'\r
52302d4d 2591\r
30fdf114 2592 if InOutStr != '':\r
79b74a03
LG
2593 if Tag.find('[' + InOutStr + ']') == -1:\r
2594 if InOutStr != 'in, out':\r
2595 ErrorMsgList.append('Line %d : in Comment, <%s> does NOT have %s ' % (CommentStartLine, (TagPartList[0] + ' ' + TagPartList[1]).replace('\n', '').replace('\r', ''), '[' + InOutStr + ']'))\r
2596 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
2597 else:\r
2598 if Tag.find('[in,out]') == -1:\r
2599 ErrorMsgList.append('Line %d : in Comment, <%s> does NOT have %s ' % (CommentStartLine, (TagPartList[0] + ' ' + TagPartList[1]).replace('\n', '').replace('\r', ''), '[' + InOutStr + ']'))\r
2600 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
2601\r
2602\r
30fdf114 2603 if Tag.find(ParamName) == -1 and ParamName != 'VOID' and ParamName != 'void':\r
79b74a03
LG
2604 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
2605 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
30fdf114 2606 Index += 1\r
52302d4d 2607\r
30fdf114
LG
2608 if Index < ParamNumber:\r
2609 ErrorMsgList.append('Line %d : Number of doxygen tags in comment less than number of function parameters' % CommentStartLine)\r
2610 PrintErrorMsg(ERROR_DOXYGEN_CHECK_FUNCTION_HEADER, 'Number of doxygen tags in comment less than number of function parameters ', TableName, CommentId)\r
2611 # VOID return type, NOT VOID*. VOID* should be matched with a doxygen tag.\r
2612 if (FuncModifier.find('VOID') != -1 or FuncModifier.find('void') != -1) and FuncModifier.find('*') == -1:\r
52302d4d 2613\r
30fdf114
LG
2614 # assume we allow a return description tag for void func. return. that's why 'DoxygenTagNumber - 1' is used instead of 'DoxygenTagNumber'\r
2615 if Index < DoxygenTagNumber - 1 or (Index < DoxygenTagNumber and DoxygenStrList[Index].startswith('@retval')):\r
2616 ErrorMsgList.append('Line %d : VOID return type need NO doxygen tags in comment' % CommentStartLine)\r
2617 PrintErrorMsg(ERROR_DOXYGEN_CHECK_FUNCTION_HEADER, 'VOID return type need no doxygen tags in comment ', TableName, CommentId)\r
2618 else:\r
52302d4d 2619 if Index < DoxygenTagNumber and not DoxygenStrList[Index].startswith('@retval') and not DoxygenStrList[Index].startswith('@return'):\r
30fdf114
LG
2620 ErrorMsgList.append('Line %d : Number of @param doxygen tags in comment does NOT match number of function parameters' % CommentStartLine)\r
2621 PrintErrorMsg(ERROR_DOXYGEN_CHECK_FUNCTION_HEADER, 'Number of @param doxygen tags in comment does NOT match number of function parameters ', TableName, CommentId)\r
2622 else:\r
2623 if ParamNumber == 0 and DoxygenTagNumber != 0 and ((FuncModifier.find('VOID') != -1 or FuncModifier.find('void') != -1) and FuncModifier.find('*') == -1):\r
2624 ErrorMsgList.append('Line %d : VOID return type need NO doxygen tags in comment' % CommentStartLine)\r
2625 PrintErrorMsg(ERROR_DOXYGEN_CHECK_FUNCTION_HEADER, 'VOID return type need NO doxygen tags in comment ', TableName, CommentId)\r
2626 if ParamNumber != 0 and DoxygenTagNumber == 0:\r
2627 ErrorMsgList.append('Line %d : No doxygen tags in comment' % CommentStartLine)\r
2628 PrintErrorMsg(ERROR_DOXYGEN_CHECK_FUNCTION_HEADER, 'No doxygen tags in comment ', TableName, CommentId)\r
2629\r
2630if __name__ == '__main__':\r
2631\r
2632# EdkLogger.Initialize()\r
2633# EdkLogger.SetLevel(EdkLogger.QUIET)\r
52302d4d 2634# CollectSourceCodeDataIntoDB(sys.argv[1])\r
b36d134f
LG
2635 try:\r
2636 test_file = sys.argv[1]\r
5b0671c1 2637 except IndexError as v:\r
72443dd2 2638 print("Usage: %s filename" % sys.argv[0])\r
b36d134f
LG
2639 sys.exit(1)\r
2640 MsgList = CheckFuncHeaderDoxygenComments(test_file)\r
30fdf114 2641 for Msg in MsgList:\r
72443dd2
GL
2642 print(Msg)\r
2643 print('Done!')\r