Home | History | Annotate | Download | only in Eot
      1 ## @file

      2 # This file is used to create report for Eot tool

      3 #

      4 # Copyright (c) 2008 - 2014, Intel Corporation. All rights reserved.<BR>

      5 # This program and the accompanying materials

      6 # are licensed and made available under the terms and conditions of the BSD License

      7 # which accompanies this distribution.  The full text of the license may be found at

      8 # http://opensource.org/licenses/bsd-license.php

      9 #

     10 # THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,

     11 # WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.

     12 #

     13 
     14 ##

     15 # Import Modules

     16 #

     17 import Common.LongFilePathOs as os
     18 import EotGlobalData
     19 from Common.LongFilePathSupport import OpenLongFilePath as open
     20 
     21 ## Report() class

     22 #

     23 #  This class defined Report

     24 #

     25 #  @param object: Inherited from object class

     26 #

     27 class Report(object):
     28     ## The constructor

     29     #

     30     #  @param  self: The object pointer

     31     #  @param  ReportName: name of the report

     32     #  @param  FvObj: FV object after parsing FV images

     33     #

     34     def __init__(self, ReportName = 'Report.html', FvObj = None, DispatchName=None):
     35         self.ReportName = ReportName
     36         self.Op = open(ReportName, 'w+')
     37         self.DispatchList = None
     38         if DispatchName:
     39             self.DispatchList = open(DispatchName, 'w+')
     40         self.FvObj = FvObj
     41         self.FfsIndex = 0
     42         self.PpiIndex = 0
     43         self.ProtocolIndex = 0
     44         if EotGlobalData.gMACRO['EFI_SOURCE'] == '':
     45             EotGlobalData.gMACRO['EFI_SOURCE'] = EotGlobalData.gMACRO['EDK_SOURCE']
     46 
     47     ## WriteLn() method

     48     #

     49     #  Write a line in the report

     50     #

     51     #  @param  self: The object pointer

     52     #  @param Line:  The lint to be written into

     53     #

     54     def WriteLn(self, Line):
     55         self.Op.write('%s\n' % Line)
     56 
     57     ## GenerateReport() method

     58     #

     59     #  A caller to generate report

     60     #

     61     #  @param  self: The object pointer

     62     #

     63     def GenerateReport(self):
     64         self.GenerateHeader()
     65         self.GenerateFv()
     66         self.GenerateTail()
     67         self.Op.close()
     68         self.GenerateUnDispatchedList()
     69 
     70     ## GenerateUnDispatchedList() method

     71     #

     72     #  Create a list for not dispatched items

     73     #

     74     #  @param  self: The object pointer

     75     #

     76     def GenerateUnDispatchedList(self):
     77         FvObj = self.FvObj
     78         EotGlobalData.gOP_UN_DISPATCHED.write('%s\n' % FvObj.Name)
     79         for Item in FvObj.UnDispatchedFfsDict:
     80             EotGlobalData.gOP_UN_DISPATCHED.write('%s\n' % FvObj.UnDispatchedFfsDict[Item])
     81 
     82     ## GenerateFv() method

     83     #

     84     #  Generate FV information

     85     #

     86     #  @param  self: The object pointer

     87     #

     88     def GenerateFv(self):
     89         FvObj = self.FvObj
     90         Content = """  <tr>
     91     <td width="20%%"><strong>Name</strong></td>
     92     <td width="60%%"><strong>Guid</strong></td>
     93     <td width="20%%"><strong>Size</strong></td>
     94   </tr>"""
     95         self.WriteLn(Content)
     96 
     97         for Info in FvObj.BasicInfo:
     98             FvName = Info[0]
     99             FvGuid = Info[1]
    100             FvSize = Info[2]
    101 
    102             Content = """  <tr>
    103     <td>%s</td>
    104     <td>%s</td>
    105     <td>%s</td>
    106   </tr>"""  % (FvName, FvGuid, FvSize)
    107             self.WriteLn(Content)
    108 
    109         Content = """    <td colspan="3"><table width="100%%"  border="1">
    110       <tr>"""
    111         self.WriteLn(Content)
    112 
    113         EotGlobalData.gOP_DISPATCH_ORDER.write('Dispatched:\n')
    114         for FfsId in FvObj.OrderedFfsDict:
    115             self.GenerateFfs(FvObj.OrderedFfsDict[FfsId])
    116         Content = """     </table></td>
    117   </tr>"""
    118         self.WriteLn(Content)
    119 
    120         # For UnDispatched

    121         Content = """    <td colspan="3"><table width="100%%"  border="1">
    122       <tr>
    123         <tr><strong>UnDispatched</strong></tr>"""
    124         self.WriteLn(Content)
    125 
    126         EotGlobalData.gOP_DISPATCH_ORDER.write('\nUnDispatched:\n')
    127         for FfsId in FvObj.UnDispatchedFfsDict:
    128             self.GenerateFfs(FvObj.UnDispatchedFfsDict[FfsId])
    129         Content = """     </table></td>
    130   </tr>"""
    131         self.WriteLn(Content)
    132 
    133     ## GenerateDepex() method

    134     #

    135     #  Generate Depex information

    136     #

    137     #  @param  self: The object pointer

    138     #  @param DepexString: A DEPEX string needed to be parsed

    139     #

    140     def GenerateDepex(self, DepexString):
    141         NonGuidList = ['AND', 'OR', 'NOT', 'BEFORE', 'AFTER', 'TRUE', 'FALSE']
    142         ItemList = DepexString.split(' ')
    143         DepexString = ''
    144         for Item in ItemList:
    145             if Item not in NonGuidList:
    146                 SqlCommand = """select DISTINCT GuidName from Report where GuidValue like '%s' and ItemMode = 'Produced' group by GuidName""" % (Item)
    147                 RecordSet = EotGlobalData.gDb.TblReport.Exec(SqlCommand)
    148                 if RecordSet != []:
    149                     Item = RecordSet[0][0]
    150             DepexString = DepexString + Item + ' '
    151         Content = """                <tr>
    152                   <td width="5%%"></td>
    153                   <td width="95%%">%s</td>
    154                 </tr>""" % (DepexString)
    155         self.WriteLn(Content)
    156 
    157     ## GeneratePpi() method

    158     #

    159     #  Generate PPI information

    160     #

    161     #  @param self: The object pointer

    162     #  @param Name: CName of a GUID

    163     #  @param Guid: Value of a GUID

    164     #  @param Type: Type of a GUID

    165     #

    166     def GeneratePpi(self, Name, Guid, Type):
    167         self.GeneratePpiProtocol('Ppi', Name, Guid, Type, self.PpiIndex)
    168 
    169     ## GenerateProtocol() method

    170     #

    171     #  Generate PROTOCOL information

    172     #

    173     #  @param self: The object pointer

    174     #  @param Name: CName of a GUID

    175     #  @param Guid: Value of a GUID

    176     #  @param Type: Type of a GUID

    177     #

    178     def GenerateProtocol(self, Name, Guid, Type):
    179         self.GeneratePpiProtocol('Protocol', Name, Guid, Type, self.ProtocolIndex)
    180 
    181     ## GeneratePpiProtocol() method

    182     #

    183     #  Generate PPI/PROTOCOL information

    184     #

    185     #  @param self: The object pointer

    186     #  @param Model: Model of a GUID, PPI or PROTOCOL

    187     #  @param Name: Name of a GUID

    188     #  @param Guid: Value of a GUID

    189     #  @param Type: Type of a GUID

    190     #  @param CName: CName(Index) of a GUID

    191     #

    192     def GeneratePpiProtocol(self, Model, Name, Guid, Type, CName):
    193         Content = """                <tr>
    194                   <td width="5%%"></td>
    195                   <td width="10%%">%s</td>
    196                   <td width="85%%" colspan="3">%s</td>
    197                   <!-- %s -->
    198                 </tr>""" % (Model, Name, Guid)
    199         self.WriteLn(Content)
    200         if Type == 'Produced':
    201             SqlCommand = """select DISTINCT SourceFileFullPath, BelongsToFunction from Report where GuidName like '%s' and ItemMode = 'Callback'""" % Name
    202             RecordSet = EotGlobalData.gDb.TblReport.Exec(SqlCommand)
    203             for Record in RecordSet:
    204                 SqlCommand = """select FullPath from File
    205                                 where ID = (
    206                                 select DISTINCT BelongsToFile from Inf
    207                                 where Value1 like '%s')""" % Record[0]
    208                 ModuleSet = EotGlobalData.gDb.TblReport.Exec(SqlCommand)
    209                 Inf = ModuleSet[0][0].replace(EotGlobalData.gMACRO['WORKSPACE'], '.')
    210                 Function = Record[1]
    211                 Address = ''
    212                 for Item in EotGlobalData.gMap:
    213                     if Function in EotGlobalData.gMap[Item]:
    214                         Address = EotGlobalData.gMap[Item][Function]
    215                         break
    216                     if '_' + Function in EotGlobalData.gMap[Item]:
    217                         Address = EotGlobalData.gMap[Item]['_' + Function]
    218                         break
    219                 Content = """                <tr>
    220                       <td width="5%%"></td>
    221                       <td width="10%%">%s</td>
    222                       <td width="40%%">%s</td>
    223                       <td width="35%%">%s</td>
    224                       <td width="10%%">%s</td>
    225                     </tr>""" % ('Callback', Inf, Function, Address)
    226                 self.WriteLn(Content)
    227 
    228     ## GenerateFfs() method

    229     #

    230     #  Generate FFS information

    231     #

    232     #  @param self: The object pointer

    233     #  @param FfsObj: FFS object after FV image is parsed

    234     #

    235     def GenerateFfs(self, FfsObj):
    236         self.FfsIndex = self.FfsIndex + 1
    237         if FfsObj != None and FfsObj.Type in [0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0xA]:
    238             FfsGuid = FfsObj.Guid
    239             FfsOffset = FfsObj._OFF_
    240             FfsName = 'Unknown-Module'
    241             FfsPath = FfsGuid
    242             FfsType = FfsObj._TypeName[FfsObj.Type]
    243 
    244             # Hard code for Binary INF

    245             if FfsGuid.upper() == '7BB28B99-61BB-11D5-9A5D-0090273FC14D':
    246                 FfsName = 'Logo'
    247 
    248             if FfsGuid.upper() == '7E374E25-8E01-4FEE-87F2-390C23C606CD':
    249                 FfsName = 'AcpiTables'
    250 
    251             if FfsGuid.upper() == '961578FE-B6B7-44C3-AF35-6BC705CD2B1F':
    252                 FfsName = 'Fat'
    253 
    254             # Find FFS Path and Name

    255             SqlCommand = """select Value2 from Inf
    256                             where BelongsToFile = (select BelongsToFile from Inf where Value1 = 'FILE_GUID' and lower(Value2) = lower('%s') and Model = %s)
    257                             and Model = %s and Value1='BASE_NAME'""" % (FfsGuid, 5001, 5001)
    258             RecordSet = EotGlobalData.gDb.TblReport.Exec(SqlCommand)
    259             if RecordSet != []:
    260                 FfsName = RecordSet[0][0]
    261 
    262             SqlCommand = """select FullPath from File
    263                             where ID = (select BelongsToFile from Inf where Value1 = 'FILE_GUID' and lower(Value2) = lower('%s') and Model = %s)
    264                             and Model = %s""" % (FfsGuid, 5001, 1011)
    265             RecordSet = EotGlobalData.gDb.TblReport.Exec(SqlCommand)
    266             if RecordSet != []:
    267                 FfsPath = RecordSet[0][0]
    268 
    269             Content = """  <tr>
    270       <tr class='styleFfs' id='FfsHeader%s'>
    271         <td width="55%%"><span onclick="Display('FfsHeader%s', 'Ffs%s')" onMouseOver="funOnMouseOver()" onMouseOut="funOnMouseOut()">%s</span></td>
    272         <td width="15%%">%s</td>
    273         <!--<td width="20%%">%s</td>-->
    274         <!--<td width="20%%">%s</td>-->
    275         <td width="10%%">%s</td>
    276       </tr>
    277       <tr id='Ffs%s' style='display:none;'>
    278         <td colspan="4"><table width="100%%"  border="1">""" % (self.FfsIndex, self.FfsIndex, self.FfsIndex, FfsPath, FfsName, FfsGuid, FfsOffset, FfsType, self.FfsIndex)
    279             
    280             if self.DispatchList:
    281                 if FfsObj.Type in [0x04, 0x06]:
    282                     self.DispatchList.write("%s %s %s %s\n" % (FfsGuid, "P", FfsName, FfsPath))
    283                 if FfsObj.Type in [0x05, 0x07, 0x08, 0x0A]:
    284                     self.DispatchList.write("%s %s %s %s\n" % (FfsGuid, "D", FfsName, FfsPath))
    285                
    286             self.WriteLn(Content)
    287 
    288             EotGlobalData.gOP_DISPATCH_ORDER.write('%s\n' %FfsName)
    289 
    290             if FfsObj.Depex != '':
    291                 Content = """          <tr>
    292             <td><span id='DepexHeader%s' class="styleDepex" onclick="Display('DepexHeader%s', 'Depex%s')" onMouseOver="funOnMouseOver()" onMouseOut="funOnMouseOut()">&nbsp&nbspDEPEX expression</span></td>
    293           </tr>
    294           <tr id='Depex%s' style='display:none;'>
    295             <td><table width="100%%"  border="1">""" % (self.FfsIndex, self.FfsIndex, self.FfsIndex, self.FfsIndex)
    296                 self.WriteLn(Content)
    297                 self.GenerateDepex(FfsObj.Depex)
    298                 Content = """            </table></td>
    299           </tr>"""
    300                 self.WriteLn(Content)
    301             # End of DEPEX

    302 
    303             # Find Consumed Ppi/Protocol

    304             SqlCommand = """select ModuleName, ItemType, GuidName, GuidValue, GuidMacro from Report
    305                             where SourceFileFullPath in
    306                             (select Value1 from Inf where BelongsToFile =
    307                             (select BelongsToFile from Inf
    308                             where Value1 = 'FILE_GUID' and Value2 like '%s' and Model = %s)
    309                             and Model = %s)
    310                             and ItemMode = 'Consumed' group by GuidName order by ItemType""" \
    311                             % (FfsGuid, 5001, 3007)
    312 
    313             RecordSet = EotGlobalData.gDb.TblReport.Exec(SqlCommand)
    314             if RecordSet != []:
    315                 Count = len(RecordSet)
    316                 Content = """          <tr>
    317             <td><span id='ConsumedHeader%s' class="styleConsumed" onclick="Display('ConsumedHeader%s', 'Consumed%s')" onMouseOver="funOnMouseOver()" onMouseOut="funOnMouseOut()">&nbsp&nbspConsumed Ppis/Protocols List (%s)</span></td>
    318           </tr>
    319           <tr id='Consumed%s' style='display:none;'>
    320             <td><table width="100%%"  border="1">""" % (self.FfsIndex, self.FfsIndex, self.FfsIndex, Count, self.FfsIndex)
    321                 self.WriteLn(Content)
    322                 self.ProtocolIndex = 0
    323                 for Record in RecordSet:
    324                     self.ProtocolIndex = self.ProtocolIndex + 1
    325                     Name = Record[2]
    326                     CName = Record[4]
    327                     Guid = Record[3]
    328                     Type = Record[1]
    329                     self.GeneratePpiProtocol(Type, Name, Guid, 'Consumed', CName)
    330 
    331                 Content = """            </table></td>
    332           </tr>"""
    333                 self.WriteLn(Content)
    334             #End of Consumed Ppi/Portocol

    335 
    336             # Find Produced Ppi/Protocol

    337             SqlCommand = """select ModuleName, ItemType, GuidName, GuidValue, GuidMacro from Report
    338                             where SourceFileFullPath in
    339                             (select Value1 from Inf where BelongsToFile =
    340                             (select BelongsToFile from Inf
    341                             where Value1 = 'FILE_GUID' and Value2 like '%s' and Model = %s)
    342                             and Model = %s)
    343                             and ItemMode = 'Produced' group by GuidName order by ItemType""" \
    344                             % (FfsGuid, 5001, 3007)
    345 
    346             RecordSet = EotGlobalData.gDb.TblReport.Exec(SqlCommand)
    347             if RecordSet != []:
    348                 Count = len(RecordSet)
    349                 Content = """          <tr>
    350             <td><span id='ProducedHeader%s' class="styleProduced" onclick="Display('ProducedHeader%s', 'Produced%s')" onMouseOver="funOnMouseOver()" onMouseOut="funOnMouseOut()">&nbsp&nbspProduced Ppis/Protocols List (%s)</span></td>
    351           </tr>
    352           <tr id='Produced%s' style='display:none;'>
    353             <td><table width="100%%"  border="1">""" % (self.FfsIndex, self.FfsIndex, self.FfsIndex, Count, self.FfsIndex)
    354                 self.WriteLn(Content)
    355                 self.PpiIndex = 0
    356                 for Record in RecordSet:
    357                     self.PpiIndex = self.PpiIndex + 1
    358                     Name = Record[2]
    359                     CName = Record[4]
    360                     Guid = Record[3]
    361                     Type = Record[1]
    362                     self.GeneratePpiProtocol(Type, Name, Guid, 'Produced', CName)
    363 
    364                 Content = """            </table></td>
    365           </tr>"""
    366                 self.WriteLn(Content)
    367             RecordSet = None
    368             # End of Produced Ppi/Protocol

    369 
    370             Content = """        </table></td>
    371         </tr>"""
    372             self.WriteLn(Content)
    373 
    374     ## GenerateTail() method

    375     #

    376     #  Generate end tags of HTML report

    377     #

    378     #  @param self: The object pointer

    379     #

    380     def GenerateTail(self):
    381         Tail = """</table>
    382 </body>
    383 </html>"""
    384         self.WriteLn(Tail)
    385 
    386     ## GenerateHeader() method

    387     #

    388     #  Generate start tags of HTML report

    389     #

    390     #  @param self: The object pointer

    391     #

    392     def GenerateHeader(self):
    393         Header = """<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
    394 "http://www.w3.org/TR/html4/loose.dtd">
    395 <html>
    396 <head>
    397 <title>Execution Order Tool Report</title>
    398 <meta http-equiv="Content-Type" content="text/html">
    399 <style type="text/css">
    400 <!--
    401 .styleFfs {
    402     color: #006600;
    403     font-weight: bold;
    404 }
    405 .styleDepex {
    406     color: #FF0066;
    407     font-weight: bold;
    408 }
    409 .styleProduced {
    410     color: #0000FF;
    411     font-weight: bold;
    412 }
    413 .styleConsumed {
    414     color: #FF00FF;
    415     font-weight: bold;
    416 }
    417 -->
    418 </style>
    419 <Script type="text/javascript">
    420 function Display(ParentID, SubID)
    421 {
    422     SubItem = document.getElementById(SubID);
    423     ParentItem = document.getElementById(ParentID);
    424     if (SubItem.style.display == 'none')
    425     {
    426         SubItem.style.display = ''
    427         ParentItem.style.fontWeight = 'normal'
    428     }
    429     else
    430     {
    431         SubItem.style.display = 'none'
    432         ParentItem.style.fontWeight = 'bold'
    433     }
    434 
    435 }
    436 
    437 function funOnMouseOver()
    438 {
    439     document.body.style.cursor = "hand";
    440 }
    441 
    442 function funOnMouseOut()
    443 {
    444     document.body.style.cursor = "";
    445 }
    446 
    447 </Script>
    448 </head>
    449 
    450 <body>
    451 <table width="100%%"  border="1">"""
    452         self.WriteLn(Header)
    453 
    454 ##

    455 #

    456 # This acts like the main() function for the script, unless it is 'import'ed into another

    457 # script.

    458 #

    459 if __name__ == '__main__':
    460     # Initialize log system

    461     FilePath = 'FVRECOVERYFLOPPY.fv'
    462     if FilePath.lower().endswith(".fv"):
    463         fd = open(FilePath, 'rb')
    464         buf = array('B')
    465         try:
    466             buf.fromfile(fd, os.path.getsize(FilePath))
    467         except EOFError:
    468             pass
    469 
    470         fv = FirmwareVolume("FVRECOVERY", buf, 0)
    471 
    472     report = Report('Report.html', fv)
    473     report.GenerateReport()
    474