[csw-devel] SF.net SVN: gar:[19266] csw/mgar/gar/v2-yann/lib/python

chninkel at users.sourceforge.net chninkel at users.sourceforge.net
Sat Sep 22 15:05:00 CEST 2012


Revision: 19266
          http://gar.svn.sourceforge.net/gar/?rev=19266&view=rev
Author:   chninkel
Date:     2012-09-22 13:05:00 +0000 (Sat, 22 Sep 2012)
Log Message:
-----------
added unit test + some fixes

Modified Paths:
--------------
    csw/mgar/gar/v2-yann/lib/python/common_constants.py
    csw/mgar/gar/v2-yann/lib/python/inspective_package.py
    csw/mgar/gar/v2-yann/lib/python/inspective_package_test.py

Modified: csw/mgar/gar/v2-yann/lib/python/common_constants.py
===================================================================
--- csw/mgar/gar/v2-yann/lib/python/common_constants.py	2012-09-22 09:38:33 UTC (rev 19265)
+++ csw/mgar/gar/v2-yann/lib/python/common_constants.py	2012-09-22 13:05:00 UTC (rev 19266)
@@ -34,6 +34,7 @@
 
 DEFAULT_INSTALL_CONTENTS_FILE = "/var/sadm/install/contents"
 DUMP_BIN = "/usr/ccs/bin/dump"
+ELFDUMP_BIN = "/usr/ccs/bin/elfdump"
 
 OWN_PKGNAME_PREFIXES = frozenset(["CSW"])
 

Modified: csw/mgar/gar/v2-yann/lib/python/inspective_package.py
===================================================================
--- csw/mgar/gar/v2-yann/lib/python/inspective_package.py	2012-09-22 09:38:33 UTC (rev 19265)
+++ csw/mgar/gar/v2-yann/lib/python/inspective_package.py	2012-09-22 13:05:00 UTC (rev 19266)
@@ -254,7 +254,8 @@
     for binary in binaries:
       binary_abspath = os.path.join(self.directory, "root", binary)
       # elfdump is the only tool that give us all informations
-      retcode, stdout, stderr = ShellCommand(["/usr/ccs/bin/elfdump", "-svy", binary_abspath])
+      args = [common_constants.ELFDUMP_BIN, "-svy", binary_abspath]
+      retcode, stdout, stderr = ShellCommand(args)
       if retcode or stderr:
         logging.error("%s returned one or more errors: %s", args, stderr)
         continue
@@ -268,7 +269,7 @@
       # the key is the original field name and the value the destination field name
       elf_fields = {'version definition': {
                       'version': 'version',
-                      'dependency': 'dependancy',
+                      'dependency': 'dependency',
                       },
                     'version needed': {
                       'file': 'soname',
@@ -277,6 +278,7 @@
                     'symbol table': {
                       'name': 'symbol',
                       'ver': 'version',
+                      'type': 'type',
                       'bind': 'bind',
                       'shndx': 'shndx',
                       },
@@ -320,6 +322,7 @@
         binary_info['version definition'].pop(0)
 
       binary_info['symbol table'] = symbols.values()
+      binary_info['symbol table'].sort(key=lambda m: m['symbol'])
       # To not rely of the section order output of elfdump, we resolve symbol version
       # informations here after having parsed all elfdump output
       self._ResolveSymbolsVersionInfo (binary_info)
@@ -337,7 +340,8 @@
       # this could be potentially moved into the DirectoryFormatPackage class.
       # ldd needs the binary to be executable
       os.chmod(binary_abspath, 0755)
-      retcode, stdout, stderr = ShellCommand(["ldd", "-Ur", binary_abspath])
+      args = ["ldd", "-Ur", binary_abspath]
+      retcode, stdout, stderr = ShellCommand(args)
       if retcode:
         uname_info = os.uname()
         if (uname_info[2] == '5.9' and uname_info[4] == 'i86pc' and
@@ -373,17 +377,21 @@
     version_info = binary_info['version definition'] + binary_info['version needed']
 
     for sym_info in binary_info['symbol table']:
-      # version index is an 1-based index on the version information table
-      # from which we also removed the first entry which was the
-      # base library/binary itself
+      # sym_info version field is an 1-based index on the version information table
+      # we don't care about 0 and 1 values:
+      #  0 is for external symbol with no version information available
+      #  1 is for a symbol defined by the binary and not binded to a version interface
+      #    but we removed that (useless) entry from the version definition table
       version_index = int(sym_info['version']) - 2
       if version_index >= 0:
         version = version_info[version_index]
         sym_info['version'] = version['version']
-        sym_info['soname'] = version['soname']
+        if 'soname' in version:
+          sym_info['soname'] = version['soname']
+      else:
+        sym_info['version'] = None
 
       # we make sure these fields are present even if the syminfo section is not
-      sym_info.setdefault('version')
       sym_info.setdefault('soname')
       sym_info.setdefault('flags')
 
@@ -410,8 +418,9 @@
       'version definition': (r"""
         \s*(?:\[(?P<index>\d+)\]\s+)? # index might be not present
                                       # if no version binding is enabled
-        (?P<version>.*\S)
-        \s+(?P<dependency>\S+)?\s*$
+        (?P<version>\S+)
+        (?:\s+(?P<dependency>\S+))?
+        (?:\s+\[\s(?:BASE)\s\])?\s*$ #
                               """),
       'version needed': (r"""
         \s*(?:\[(?P<index>\d+)\]\s+)?     # index might be not present
@@ -428,21 +437,21 @@
          \s*\[\d+\]
          \s+(?:0x[0-9a-f]+|REG_G\d+)
          \s+0x[0-9a-f]+
-         \s+\S+
+         \s+(?P<type>\S+)
          \s+(?P<bind>\S+)
          \s+\S+
          \s+(?P<ver>\S+)
          \s+(?P<shndx>\S+)
-         \s+(?P<name>\S+)?\s*$
+         (?:\s+(?P<name>\S+))?\s*$
                         """),
       'syminfo': (r"""
          \s*\[\d+\]
          \s+(?P<flags>[ABCDFILNPS]+)
          \s+(?:(?:\[\d+\]                   # some kind of library index
-         \s+(?P<library>.*\S)|<self>)\s+)?  # library is not present
+         \s+(?P<library>\S+)|<self>)\s+)?  # library is not present
                                             # for external symbols not
                                             # directly bound
-         (?P<symbol>.*\S)\s*
+         (?P<symbol>\S+)\s*
                    """)}
 
     elfdump_data = None

Modified: csw/mgar/gar/v2-yann/lib/python/inspective_package_test.py
===================================================================
--- csw/mgar/gar/v2-yann/lib/python/inspective_package_test.py	2012-09-22 09:38:33 UTC (rev 19265)
+++ csw/mgar/gar/v2-yann/lib/python/inspective_package_test.py	2012-09-22 13:05:00 UTC (rev 19266)
@@ -6,6 +6,7 @@
 import hachoir_parser
 import magic
 import os
+import common_constants
 
 LDD_R_OUTPUT_1 =  """\tlibc.so.1 =>  /lib/libc.so.1
 \tsymbol not found: check_encoding_conversion_args    (/opt/csw/lib/postgresql/8.4/utf8_and_gbk.so)
@@ -69,6 +70,89 @@
     self.assertEqual([u'/fake/path/CSWfoo/root/foo-file'], ip.ListBinaries())
 
 
+
+
+  def testGetBinaryElfInfo(self):
+
+    fake_binary = 'opt/csw/lib/libssl.so.1.0.0'
+    fake_package_path = '/fake/path/CSWfoo'
+    fake_elfdump_output = '''
+Version Definition Section:  .SUNW_version
+     index  version                     dependency
+       [1]  libssl.so.1.0.0                                  [ BASE ]
+       [2]  OPENSSL_1.0.0
+       [3]  OPENSSL_1.0.1               OPENSSL_1.0.0
+
+Version Needed Section:  .SUNW_version
+     index  file                        version
+       [4]  libcrypto.so.1.0.0          OPENSSL_1.0.0        [ INFO ]
+       [5]                              OPENSSL_1.0.1
+       [6]  libnsl.so.1                 SUNW_1.9.1
+
+Symbol Table Section:  .dynsym
+     index    value      size      type bind oth ver shndx          name
+       [0]  0x00000000 0x00000000  NOTY LOCL  D    0 UNDEF
+       [1]  0x00000000 0x00000000  FUNC GLOB  D    4 UNDEF          EVP_DigestSignFinal
+       [2]  0x0003ead4 0x000000dc  FUNC GLOB  P    2 .text          SSL_get_shared_ciphers
+       [3]  0x0004f8f8 0x00000014  FUNC GLOB  P    3 .text          SSL_CTX_set_srp_client_pwd_callback
+       [4]  0x00000000 0x00000000  FUNC GLOB  D    5 UNDEF          SRP_Calc_client_key
+       [5]  0x000661a0 0x00000000  OBJT GLOB  P    1 .got           _GLOBAL_OFFSET_TABLE_
+
+Syminfo Section:  .SUNW_syminfo
+     index  flags            bound to                 symbol
+       [1]  DBL          [1] libcrypto.so.1.0.0       EVP_DigestSignFinal
+       [2]  DB               <self>                   SSL_get_shared_ciphers
+       [3]  DB               <self>                   SSL_CTX_set_srp_client_pwd_callback
+       [4]  DBL          [1] libcrypto.so.1.0.0       SRP_Calc_client_key
+       [5]  DB               <self>                   _GLOBAL_OFFSET_TABLE_
+'''
+    fake_binary_elfinfo = {'opt/csw/lib/libssl.so.1.0.0': {
+      'symbol table': [
+        {'shndx': 'UNDEF', 'soname': None, 'bind': 'LOCL',
+          'symbol': None, 'version': None, 'flags': None, 'type': 'NOTY'},
+        {'shndx': 'UNDEF', 'soname': 'libcrypto.so.1.0.0', 'bind': 'GLOB',
+          'symbol': 'EVP_DigestSignFinal', 'version': 'OPENSSL_1.0.0',
+          'flags': 'DBL', 'type': 'FUNC'},
+        {'shndx': 'UNDEF', 'soname': 'libcrypto.so.1.0.0', 'bind': 'GLOB',
+          'symbol': 'SRP_Calc_client_key', 'version': 'OPENSSL_1.0.1',
+          'flags': 'DBL', 'type': 'FUNC'},
+        {'shndx': '.text', 'soname': None, 'bind': 'GLOB',
+          'symbol': 'SSL_CTX_set_srp_client_pwd_callback',
+          'version': 'OPENSSL_1.0.1', 'flags': 'DB', 'type': 'FUNC'},
+        {'shndx': '.text', 'soname': None, 'bind': 'GLOB',
+          'symbol': 'SSL_get_shared_ciphers', 'version': 'OPENSSL_1.0.0',
+          'flags': 'DB', 'type': 'FUNC'},
+        {'shndx': '.got', 'soname': None, 'bind': 'GLOB',
+          'symbol': '_GLOBAL_OFFSET_TABLE_', 'version': None,
+          'flags': 'DB', 'type': 'OBJT'},
+        ],
+      'version definition': [
+        {'dependency': None, 'version': 'OPENSSL_1.0.0'},
+        {'dependency': 'OPENSSL_1.0.0', 'version': 'OPENSSL_1.0.1'},
+        ],
+      'version needed': [
+        {'version': 'OPENSSL_1.0.0', 'soname': 'libcrypto.so.1.0.0'},
+        {'version': 'OPENSSL_1.0.1', 'soname': 'libcrypto.so.1.0.0'},
+        {'version': 'SUNW_1.9.1', 'soname': 'libnsl.so.1'},
+        ]
+      }
+    }
+
+    ip = inspective_package.InspectivePackage(fake_package_path)
+    self.mox.StubOutWithMock(ip, 'ListBinaries')
+    ip.ListBinaries().AndReturn([fake_binary])
+
+    self.mox.StubOutWithMock(inspective_package, 'ShellCommand')
+    args = [common_constants.ELFDUMP_BIN,
+            '-svy',
+            os.path.join(fake_package_path, "root", fake_binary)]
+    inspective_package.ShellCommand(args).AndReturn((0, fake_elfdump_output, ""))
+    self.mox.ReplayAll()
+
+    self.assertEqual(fake_binary_elfinfo, ip.GetBinaryElfInfo())
+
+
+
 class PackageStatsUnitTest(unittest.TestCase):
 
   def setUp(self):
@@ -80,7 +164,7 @@
 
   def test_ParseElfdumpLineVersionNeeded(self):
     line = '[13]                              SUNW_0.9             [ INFO ]'
-    expected = { 
+    expected = {
         'index': '13',
 	'version': 'SUNW_0.9',
 	'file': None
@@ -89,11 +173,12 @@
 
   def test_ParseElfdumpLineSymbolTable(self):
     line = '    [9]  0x000224b8 0x0000001c  FUNC GLOB  D    1 .text          vsf_log_line'
-    expected = { 
-        'bind': 'GLOB',
-	'shndx': '.text',
-	'name': 'vsf_log_line',
-	'ver': '1'
+    expected = {
+      'bind': 'GLOB',
+      'shndx': '.text',
+      'name': 'vsf_log_line',
+      'ver': '1',
+      'type': 'FUNC',
     }
     self.assertEqual((expected, 'symbol table'), self.ip._ParseElfdumpLine(line, 'symbol table'))
 

This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.



More information about the devel mailing list