components/crash/content/tools/generate_breakpad_symbols.py
def GetSharedLibraryDependenciesMac(binary, exe_path):
  """Return absolute paths to all shared library dependencies of the binary.

  This implementation assumes that we're running on a Mac system."""
  # realpath() serves two purposes:
  # 1. If an executable is linked against a framework, it links against
  #    Framework.framework/Framework, which is a symlink to
  #    Framework.framework/Framework/Versions/A/Framework. rpaths are relative
  #    to the real location, so resolving the symlink is important.
  # 2. It converts binary to an absolute path. If binary is just
  #    "foo.dylib" in the current directory, dirname() would return an empty
  #    string, causing "@loader_path/foo" to incorrectly expand to "/foo".
  loader_path = os.path.dirname(os.path.realpath(binary))
  env = os.environ.copy()

  SRC_ROOT_PATH = os.path.join(os.path.dirname(__file__), '../../../..')
  hermetic_otool_path = os.path.join(
      SRC_ROOT_PATH, 'build', 'mac_files', 'xcode_binaries', 'Contents',
      'Developer', 'Toolchains', 'XcodeDefault.xctoolchain', 'usr', 'bin',
      'otool')
  if os.path.exists(hermetic_otool_path):
    otool_path = hermetic_otool_path
  else:
    developer_dir = GetDeveloperDirMac()
    if developer_dir:
      env['DEVELOPER_DIR'] = developer_dir
    otool_path = 'otool'

  otool = subprocess.check_output(
      [otool_path, '-lm', binary], env=env).decode('utf-8').splitlines()
  rpaths = []
  dylib_id = None
  for idx, line in enumerate(otool):
    if line.find('cmd LC_RPATH') != -1:
      m = re.match(' *path (.*) \(offset .*\)$', otool[idx+2])
      rpath = m.group(1)
      rpath = rpath.replace('@loader_path', loader_path)
      rpath = rpath.replace('@executable_path', exe_path)
      rpaths.append(rpath)
    elif line.find('cmd LC_ID_DYLIB') != -1:
      m = re.match(' *name (.*) \(offset .*\)$', otool[idx+2])
      dylib_id = m.group(1)
  # `man dyld` says that @rpath is resolved against a stack of LC_RPATHs from
  # all executable images leading to the load of the current module. This is
  # intentionally not implemented here, since we require that every .dylib
  # contains all the rpaths it needs on its own, without relying on rpaths of
  # the loading executables.

  otool = subprocess.check_output(
      [otool_path, '-Lm', binary], env=env).decode('utf-8').splitlines()
  lib_re = re.compile('\t(.*) \(compatibility .*\)$')
  deps = []
  for line in otool:
    m = lib_re.match(line)
    if m:
      # For frameworks and shared libraries, `otool -L` prints the LC_ID_DYLIB
      # as the first line. Filter that out.
      if m.group(1) == dylib_id:
        continue
      dep = Resolve(m.group(1), exe_path, loader_path, rpaths)
      if dep:
        deps.append(os.path.normpath(dep))
      else:
        print((
            'ERROR: failed to resolve %s, exe_path %s, loader_path %s, '
            'rpaths %s' % (m.group(1), exe_path, loader_path,
                           ', '.join(rpaths))), file=sys.stderr)
        sys.exit(1)
  return deps
Return absolute paths to all shared library dependencies of the binary.

  This implementation assumes that we're running on a Mac system.
Return absolute paths to all shared library dependencies of the binary.
This implementation assumes that we're running on a Mac system.
Return absolute paths to all shared library dependencies of the binary . This implementation assumes that we ' re running on a Mac system .
def GetSharedLibraryDependenciesMac(binary, exe_path):
  loader_path = os.path.dirname(os.path.realpath(binary))
  env = os.environ.copy()
  SRC_ROOT_PATH = os.path.join(os.path.dirname(__file__), '../../../..')
  hermetic_otool_path = os.path.join(
      SRC_ROOT_PATH, 'build', 'mac_files', 'xcode_binaries', 'Contents',
      'Developer', 'Toolchains', 'XcodeDefault.xctoolchain', 'usr', 'bin',
      'otool')
  if os.path.exists(hermetic_otool_path):
    otool_path = hermetic_otool_path
  else:
    developer_dir = GetDeveloperDirMac()
    if developer_dir:
      env['DEVELOPER_DIR'] = developer_dir
    otool_path = 'otool'
  otool = subprocess.check_output(
      [otool_path, '-lm', binary], env=env).decode('utf-8').splitlines()
  rpaths = []
  dylib_id = None
  for idx, line in enumerate(otool):
    if line.find('cmd LC_RPATH') != -1:
      m = re.match(' *path (.*) \(offset .*\)$', otool[idx+2])
      rpath = m.group(1)
      rpath = rpath.replace('@loader_path', loader_path)
      rpath = rpath.replace('@executable_path', exe_path)
      rpaths.append(rpath)
    elif line.find('cmd LC_ID_DYLIB') != -1:
      m = re.match(' *name (.*) \(offset .*\)$', otool[idx+2])
      dylib_id = m.group(1)
  otool = subprocess.check_output(
      [otool_path, '-Lm', binary], env=env).decode('utf-8').splitlines()
  lib_re = re.compile('\t(.*) \(compatibility .*\)$')
  deps = []
  for line in otool:
    m = lib_re.match(line)
    if m:
      if m.group(1) == dylib_id:
        continue
      dep = Resolve(m.group(1), exe_path, loader_path, rpaths)
      if dep:
        deps.append(os.path.normpath(dep))
      else:
        print((
            'ERROR: failed to resolve %s, exe_path %s, loader_path %s, '
            'rpaths %s' % (m.group(1), exe_path, loader_path,
                           ', '.join(rpaths))), file=sys.stderr)
        sys.exit(1)
  return deps
def GetSharedLibraryDependenciesMac ( binary , exe_path ) : loader_path = os . path . dirname ( os . path . realpath ( binary ) ) env = os . environ . copy ( ) SRC_ROOT_PATH = os . path . join ( os . path . dirname ( __file__ ) , '../../../..' ) hermetic_otool_path = os . path . join ( SRC_ROOT_PATH , 'build' , 'mac_files' , 'xcode_binaries' , 'Contents' , 'Developer' , 'Toolchains' , 'XcodeDefault.xctoolchain' , 'usr' , 'bin' , 'otool' ) if os . path . exists ( hermetic_otool_path ) : otool_path = hermetic_otool_path else : developer_dir = GetDeveloperDirMac ( ) if developer_dir : env [ 'DEVELOPER_DIR' ] = developer_dir otool_path = 'otool' otool = subprocess . check_output ( [ otool_path , '-lm' , binary ] , env = env ) . decode ( 'utf-8' ) . splitlines ( ) rpaths = [ ] dylib_id = None for idx , line in enumerate ( otool ) : if line . find ( 'cmd LC_RPATH' ) != - 1 : m = re . match ( ' *path (.*) \(offset .*\)$' , otool [ idx + 2 ] ) rpath = m . group ( 1 ) rpath = rpath . replace ( '@loader_path' , loader_path ) rpath = rpath . replace ( '@executable_path' , exe_path ) rpaths . append ( rpath ) elif line . find ( 'cmd LC_ID_DYLIB' ) != - 1 : m = re . match ( ' *name (.*) \(offset .*\)$' , otool [ idx + 2 ] ) dylib_id = m . group ( 1 ) otool = subprocess . check_output ( [ otool_path , '-Lm' , binary ] , env = env ) . decode ( 'utf-8' ) . splitlines ( ) lib_re = re . compile ( '\t(.*) \(compatibility .*\)$' ) deps = [ ] for line in otool : m = lib_re . match ( line ) if m : if m . group ( 1 ) == dylib_id : continue dep = Resolve ( m . group ( 1 ) , exe_path , loader_path , rpaths ) if dep : deps . append ( os . path . normpath ( dep ) ) else : print ( ( 'ERROR: failed to resolve %s, exe_path %s, loader_path %s, ' 'rpaths %s' % ( m . group ( 1 ) , exe_path , loader_path , ', ' . join ( rpaths ) ) ) , file = sys . stderr ) sys . exit ( 1 ) return deps
Return absolute paths to all shared library dependencies of the binary.
Return absolute paths to all shared library dependencies of the binary .
"""Return absolute paths to all shared library dependencies of the binary.

  This implementation assumes that we're running on a Mac system.""" # realpath() serves two purposes: # 1. If an executable is linked against a framework, it links against #    Framework.framework/Framework, which is a symlink to #    Framework.framework/Framework/Versions/A/Framework. rpaths are relative #    to the real location, so resolving the symlink is important. # 2. It converts binary to an absolute path. If binary is just #    "foo.dylib" in the current directory, dirname() would return an empty #    string, causing "@loader_path/foo" to incorrectly expand to "/foo". # `man dyld` says that @rpath is resolved against a stack of LC_RPATHs from # all executable images leading to the load of the current module. This is # intentionally not implemented here, since we require that every .dylib # contains all the rpaths it needs on its own, without relying on rpaths of # the loading executables. # For frameworks and shared libraries, `otool -L` prints the LC_ID_DYLIB # as the first line. Filter that out.
binary
exe_path