ruby-macho 0.0.7 → 0.0.8
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/lib/macho/fat_file.rb +12 -1
- data/lib/macho/load_commands.rb +6 -0
- data/lib/macho/macho_file.rb +66 -3
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 2b104665e169f8988913d6032d3755032d814a2f
|
4
|
+
data.tar.gz: fc3f95ed644f84e913a78709227e178f33e9e995
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 986523ca44a54d65a2d1624b31cbd612f520bab44ffaf405971052174224e9fedde4aabf1aa5d91fe451ee58cde5d892d95030bf6dad8f4688389fe8fc3f18dd
|
7
|
+
data.tar.gz: b5e6ffe8212660e32ed089d7dba2294818257aeb523b8eac8a3d4d66b9a549a210b40037109c26ff2cd31e47c7921fbe3389153b86dff30816efab83a061cbd4
|
data/lib/macho/fat_file.rb
CHANGED
@@ -48,12 +48,23 @@ module MachO
|
|
48
48
|
end
|
49
49
|
|
50
50
|
def linked_dylibs
|
51
|
-
dylibs = machos.map(&:linked_dylibs)
|
51
|
+
dylibs = machos.map(&:linked_dylibs).flatten
|
52
52
|
|
53
53
|
# can machos inside fat binaries have different dylibs?
|
54
54
|
dylibs.uniq!
|
55
55
|
end
|
56
56
|
|
57
|
+
# stub
|
58
|
+
def change_dylib(old_path, new_path)
|
59
|
+
machos.each do |macho|
|
60
|
+
macho.change_install_name(old_path, new_path)
|
61
|
+
end
|
62
|
+
|
63
|
+
synchronize_raw_data
|
64
|
+
end
|
65
|
+
|
66
|
+
alias :change_install_name :change_dylib
|
67
|
+
|
57
68
|
def write(filename)
|
58
69
|
File.open(filename, "wb") { |f| f.write(@raw_data) }
|
59
70
|
end
|
data/lib/macho/load_commands.rb
CHANGED
@@ -163,6 +163,12 @@ module MachO
|
|
163
163
|
SEG_UNIXSTACK = "__UNIXSTACK"
|
164
164
|
SEG_IMPORT = "__IMPORT"
|
165
165
|
|
166
|
+
# constant bits for flags in SegmentCommand, SegmentCommand64
|
167
|
+
SG_HIGHVM = 0x1
|
168
|
+
SG_FVMLIB = 0x2
|
169
|
+
SG_NORELOC = 0x4
|
170
|
+
SG_PROTECTED_VERSION_1 = 0x8
|
171
|
+
|
166
172
|
# Mach-O load command structure
|
167
173
|
# this is the most generic load command - only cmd ID and size are
|
168
174
|
# represented, and no actual data. used when a more specific class
|
data/lib/macho/macho_file.rb
CHANGED
@@ -217,11 +217,74 @@ module MachO
|
|
217
217
|
dylibs
|
218
218
|
end
|
219
219
|
|
220
|
-
#
|
221
|
-
def change_dylib
|
222
|
-
|
220
|
+
# TODO: genericize change_dylib and dylib_id= for DRYness
|
221
|
+
def change_dylib(old_path, new_path)
|
222
|
+
idx = linked_dylibs.index(old_path)
|
223
|
+
raise DylibUnknownError.new(old_path) if idx.nil?
|
224
|
+
|
225
|
+
# this is a bit of a hack - since there is a 1-1 ordered association
|
226
|
+
# between linked_dylibs and command('LC_LOAD_DYLIB'), we can use
|
227
|
+
# their indices interchangeably to avoid having to loop.
|
228
|
+
dylib_cmd = command('LC_LOAD_DYLIB')[idx]
|
229
|
+
|
230
|
+
if magic32?
|
231
|
+
cmd_round = 4
|
232
|
+
else
|
233
|
+
cmd_round = 8
|
234
|
+
end
|
235
|
+
|
236
|
+
new_sizeofcmds = header[:sizeofcmds]
|
237
|
+
old_install_name = old_path.dup
|
238
|
+
new_install_name = new_path.dup
|
239
|
+
|
240
|
+
old_pad = MachO.round(old_install_name.size, cmd_round) - old_install_name.size
|
241
|
+
new_pad = MachO.round(new_install_name.size, cmd_round) - new_install_name.size
|
242
|
+
|
243
|
+
old_install_name << "\x00" * old_pad
|
244
|
+
new_install_name << "\x00" * new_pad
|
245
|
+
|
246
|
+
new_size = DylibCommand.bytesize + new_install_name.size
|
247
|
+
new_sizeofcmds += new_size - dylib_cmd.cmdsize
|
248
|
+
|
249
|
+
low_fileoff = 2**64
|
250
|
+
|
251
|
+
segments.each do |seg|
|
252
|
+
sections(seg).each do |sect|
|
253
|
+
if sect.size != 0 && !sect.flag?(S_ZEROFILL) &&
|
254
|
+
!sect.flag?(S_THREAD_LOCAL_ZEROFILL) &&
|
255
|
+
sect.offset < low_fileoff
|
256
|
+
|
257
|
+
low_fileoff = sect.offset
|
258
|
+
end
|
259
|
+
end
|
260
|
+
end
|
261
|
+
|
262
|
+
if new_sizeofcmds + header.bytesize > low_fileoff
|
263
|
+
raise HeaderPadError.new(@filename)
|
264
|
+
end
|
265
|
+
|
266
|
+
set_sizeofcmds(new_sizeofcmds)
|
267
|
+
|
268
|
+
@raw_data[dylib_cmd.offset + 4, 4] = [new_size].pack("V")
|
269
|
+
|
270
|
+
@raw_data.slice!(dylib_cmd.offset + dylib_cmd.name...dylib_cmd.offset + dylib_cmd.class.bytesize + old_install_name.size)
|
271
|
+
|
272
|
+
@raw_data.insert(dylib_cmd.offset + dylib_cmd.name, new_install_name)
|
273
|
+
|
274
|
+
null_pad = old_install_name.size - new_install_name.size
|
275
|
+
|
276
|
+
if null_pad < 0
|
277
|
+
@raw_data.slice!(new_sizeofcmds + header.bytesize, null_pad.abs)
|
278
|
+
else
|
279
|
+
@raw_data.insert(new_sizeofcmds + header.bytesize, "\x00" * null_pad)
|
280
|
+
end
|
281
|
+
|
282
|
+
header = get_mach_header
|
283
|
+
load_commands = get_load_commands
|
223
284
|
end
|
224
285
|
|
286
|
+
alias :change_install_name :change_dylib
|
287
|
+
|
225
288
|
# get all sections in a segment by name
|
226
289
|
def sections(segment)
|
227
290
|
sections = []
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: ruby-macho
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.8
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- William Woodruff
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2015-10-
|
11
|
+
date: 2015-10-21 00:00:00.000000000 Z
|
12
12
|
dependencies: []
|
13
13
|
description: A library for viewing and manipulating Mach-O files in Ruby.
|
14
14
|
email: william@tuffbizz.com
|