fix_homebrew_paths_in_standalone_zip.py 2.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566
  1. # ------------------------------------------------------------------------------
  2. # This file is part of cpp-ethereum.
  3. #
  4. # cpp-ethereum is free software: you can redistribute it and/or modify
  5. # it under the terms of the GNU General Public License as published by
  6. # the Free Software Foundation, either version 3 of the License, or
  7. # (at your option) any later version.
  8. #
  9. # cpp-ethereum is distributed in the hope that it will be useful,
  10. # but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  12. # GNU General Public License for more details.
  13. #
  14. # You should have received a copy of the GNU General Public License
  15. # along with cpp-ethereum. If not, see <http://www.gnu.org/licenses/>
  16. #
  17. # -----------------------------------------------------------------------------
  18. #
  19. # This Python script is used within the OS X release process, to ensure
  20. # that the standalone OS X ZIP files which we make are actually
  21. # standalone, and not implicitly dependent on Homebrew installs for
  22. # external libraries which we use.
  23. #
  24. # This implicit dependencies seem to show up only where we have
  25. # external dependencies which are dependent on each other, and the
  26. # path from one to another is an absolute path to "/usr/local/opt",
  27. # the Homebrew install location. External dependencies which only
  28. # depend on system libraries are fine. Our main applications seem
  29. # to be fine.
  30. #
  31. # An example of a dependency which requires this fix-up at the time
  32. # of writing is the following dependency edge:
  33. #
  34. # libjsonrpccpp-client.0.dylib
  35. # -> /usr/local/opt/jsoncpp/lib/libjsoncpp.0.dylib
  36. #
  37. # See https://blogs.oracle.com/dipol/entry/dynamic_libraries_rpath_and_mac
  38. # for a little overview of "install_name_tool" and "otool".
  39. #
  40. # -----------------------------------------------------------------------------
  41. import os
  42. import subprocess
  43. import sys
  44. def readDependencies(fname):
  45. with open(fname) as f:
  46. o = subprocess.Popen(['otool', '-L', fname], stdout=subprocess.PIPE)
  47. for line in o.stdout:
  48. if line[0] == '\t':
  49. library = line.split(' ', 1)[0][1:]
  50. if library.startswith("/usr/local/lib") or library.startswith("/usr/local/opt") or library.startswith("/Users/"):
  51. if (os.path.basename(library) != os.path.basename(fname)):
  52. command = "install_name_tool -change " + \
  53. library + " @executable_path/./" + \
  54. os.path.basename(library) + " " + fname
  55. print command
  56. os.system("chmod +w " + fname)
  57. os.system(command)
  58. root = sys.argv[1]
  59. for (dirpath, dirnames, filenames) in os.walk(root):
  60. for filename in filenames:
  61. readDependencies(os.path.join(root, filename))