brew/Library/Homebrew/keg_relocate.rb

108 lines
2.5 KiB
Ruby
Raw Normal View History

2014-06-26 19:06:31 -05:00
class Keg
PREFIX_PLACEHOLDER = "@@HOMEBREW_PREFIX@@".freeze
CELLAR_PLACEHOLDER = "@@HOMEBREW_CELLAR@@".freeze
def fix_dynamic_linkage
2015-09-11 16:32:14 +08:00
symlink_files.each do |file|
link = file.readlink
# Don't fix relative symlinks
next unless link.absolute?
if link.to_s.start_with?(HOMEBREW_CELLAR.to_s) || link.to_s.start_with?(HOMEBREW_PREFIX.to_s)
FileUtils.ln_sf(link.relative_path_from(file.parent), file)
end
end
end
alias generic_fix_dynamic_linkage fix_dynamic_linkage
def relocate_dynamic_linkage(old_prefix, new_prefix, old_cellar, new_cellar)
[]
end
def relocate_text_files(old_prefix, new_prefix, old_cellar, new_cellar)
2015-07-23 16:29:37 +08:00
files = text_files | libtool_files
files.group_by { |f| f.stat.ino }.each_value do |first, *rest|
s = first.open("rb", &:read)
changed = s.gsub!(old_cellar, new_cellar)
changed = s.gsub!(old_prefix, new_prefix) || changed
next unless changed
begin
first.atomic_write(s)
rescue SystemCallError
first.ensure_writable do
first.open("wb") { |f| f.write(s) }
end
else
rest.each { |file| FileUtils.ln(first, file, :force => true) }
end
end
end
def detect_cxx_stdlibs(options = {})
[]
end
def each_unique_file_matching(string)
Utils.popen_read("/usr/bin/fgrep", "-lr", string, to_s) do |io|
hardlinks = Set.new
until io.eof?
file = Pathname.new(io.readline.chomp)
next if file.symlink?
yield file if hardlinks.add? file.stat.ino
end
end
end
2014-06-26 19:06:31 -05:00
def lib
path.join("lib")
end
def text_files
text_files = []
return text_files unless File.exist?("/usr/bin/file")
path.find do |pn|
next if pn.symlink? || pn.directory?
next if Metafiles::EXTENSIONS.include? pn.extname
keg_relocate: work around `file` bug There's an old bug in `file` which means it can't read certain files under a non-C locale. This has been fixed upstream for some time, but Apple hasn't picked that fix up & even on OS X El Capitan the `file` is ancient. This is currently causing a lot of false positives in our bottle code around relocating things like manpages translated into non-English languages, because currently the test does: ``` pn = "/usr/local/Cellar/vim/7.4.2109/share/man/fr/man1/vim.1" Utils.popen_read("/usr/bin/file", "--brief", pn).include?("text") ``` Which returns `false`. But it isn't returning `false` because the actual result is false, but because `file` panics & fails, which for us equals a `false`. The actual output when accessed is: ``` pn = "/usr/local/Cellar/vim/7.4.2109/share/man/fr/man1/vim.1" Utils.popen_read("/usr/bin/file", "--brief", pn) "ERROR: line 22: regexec error 17, (illegal byte sequence)\n" ``` Forcing this check to be done under a "C" locale eliminates this particular false positive for strings we can't relocate & consequently things such as NLS may prove to be more portable in some formulae than is currently the case. Using `vim` again for the example: ``` pn = "/usr/local/Cellar/vim/7.4.2109/share/man/fr/man1/vim.1" Utils.popen_read("/usr/bin/file", "--brief", pn).include?("text") true ``` This reduces the flagged strings from `vim` from 4 issues to 2, the remaining two with the `vim` executable itself which "remembers" the full path to perl, python, ruby, etc during build & vomits that information out when requested by the user. Both the manpages flagged before this change are no longer flagged as unrelocatable. This won't entirely resolve the NLS problem because some things hardcode in a locale path, which will be stored in the executable, but at the very least it should reduce the number of false positives & may enable relocation where that locale path hasn't been burnt in.
2016-08-01 04:29:23 +01:00
# File has known issues with reading files on other locales.
# http://bugs.gw.com/view.php?id=292
with_custom_locale("C") do
if Utils.popen_read("/usr/bin/file", "--brief", pn).include?("text") ||
pn.text_executable?
text_files << pn
end
end
end
text_files
end
2015-07-23 16:29:37 +08:00
def libtool_files
libtool_files = []
path.find do |pn|
next if pn.symlink? || pn.directory? || pn.extname != ".la"
2015-07-23 16:29:37 +08:00
libtool_files << pn
end
2015-07-23 16:29:37 +08:00
libtool_files
end
2015-09-11 16:32:14 +08:00
def symlink_files
symlink_files = []
path.find do |pn|
symlink_files << pn if pn.symlink?
end
symlink_files
end
def self.file_linked_libraries(file, string)
[]
end
end
require "extend/os/keg_relocate"