minitar 0.12.1 → 1.0.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -1,9 +1,7 @@
1
- # coding: utf-8
1
+ require "minitar/writer"
2
2
 
3
- require "archive/tar/minitar/writer"
4
-
5
- module Archive::Tar::Minitar
6
- # Wraps a Archive::Tar::Minitar::Writer with convenience methods and wrapped
3
+ class Minitar
4
+ # Wraps a Minitar::Writer with convenience methods and wrapped
7
5
  # stream management. If the stream provided to Output does not support random
8
6
  # access, only Writer#add_file_simple and Writer#mkdir are guaranteed to
9
7
  # work.
@@ -15,8 +13,8 @@ module Archive::Tar::Minitar
15
13
  # instance, +Output.open+ returns the value of the block.
16
14
  #
17
15
  # call-seq:
18
- # Archive::Tar::Minitar::Output.open(io) -> output
19
- # Archive::Tar::Minitar::Output.open(io) { |output| block } -> obj
16
+ # Minitar::Output.open(io) -> output
17
+ # Minitar::Output.open(io) { |output| block } -> obj
20
18
  def self.open(output)
21
19
  stream = new(output)
22
20
  return stream unless block_given?
@@ -35,8 +33,8 @@ module Archive::Tar::Minitar
35
33
  # will be created with the same behaviour.
36
34
  #
37
35
  # call-seq:
38
- # Archive::Tar::Minitar::Output.tar(io) -> enumerator
39
- # Archive::Tar::Minitar::Output.tar(io) { |tar| block } -> obj
36
+ # Minitar::Output.tar(io) -> enumerator
37
+ # Minitar::Output.tar(io) { |tar| block } -> obj
40
38
  def self.tar(output)
41
39
  return to_enum(__method__, output) unless block_given?
42
40
 
@@ -51,15 +49,15 @@ module Archive::Tar::Minitar
51
49
  # object wrapped will be closed.
52
50
  #
53
51
  # call-seq:
54
- # Archive::Tar::Minitar::Output.new(io) -> output
55
- # Archive::Tar::Minitar::Output.new(path) -> output
52
+ # Minitar::Output.new(io) -> output
53
+ # Minitar::Output.new(path) -> output
56
54
  def initialize(output)
57
55
  @io = if output.respond_to?(:write)
58
56
  output
59
57
  else
60
58
  ::Kernel.open(output, "wb")
61
59
  end
62
- @tar = Archive::Tar::Minitar::Writer.new(@io)
60
+ @tar = Minitar::Writer.new(@io)
63
61
  end
64
62
 
65
63
  # Returns the Writer object for direct access.
@@ -0,0 +1,267 @@
1
+ class Minitar
2
+ # Implements the POSIX tar header as a Ruby class. The structure of
3
+ # the POSIX tar header is:
4
+ #
5
+ # struct tarfile_entry_posix
6
+ # { // pack/unpack
7
+ # char name[100]; // ASCII (+ Z unless filled) a100/Z100
8
+ # char mode[8]; // 0 padded, octal, null a8 /A8
9
+ # char uid[8]; // 0 padded, octal, null a8 /A8
10
+ # char gid[8]; // 0 padded, octal, null a8 /A8
11
+ # char size[12]; // 0 padded, octal, null a12 /A12
12
+ # char mtime[12]; // 0 padded, octal, null a12 /A12
13
+ # char checksum[8]; // 0 padded, octal, null, space a8 /A8
14
+ # char typeflag[1]; // see below a /a
15
+ # char linkname[100]; // ASCII + (Z unless filled) a100/Z100
16
+ # char magic[6]; // "ustar\0" a6 /A6
17
+ # char version[2]; // "00" a2 /A2
18
+ # char uname[32]; // ASCIIZ a32 /Z32
19
+ # char gname[32]; // ASCIIZ a32 /Z32
20
+ # char devmajor[8]; // 0 padded, octal, null a8 /A8
21
+ # char devminor[8]; // 0 padded, octal, null a8 /A8
22
+ # char prefix[155]; // ASCII (+ Z unless filled) a155/Z155
23
+ # };
24
+ #
25
+ # The #typeflag is one of several known values.
26
+ #
27
+ # POSIX indicates that "A POSIX-compliant implementation must treat any
28
+ # unrecognized typeflag value as a regular file."
29
+ class PosixHeader
30
+ BLOCK_SIZE = 512
31
+ MAGIC_BYTES = "ustar".freeze
32
+
33
+ GNU_EXT_LONG_LINK = "././@LongLink"
34
+
35
+ # Fields that must be set in a POSIX tar(1) header.
36
+ REQUIRED_FIELDS = [:name, :size, :prefix, :mode].freeze
37
+ # Fields that may be set in a POSIX tar(1) header.
38
+ OPTIONAL_FIELDS = [
39
+ :uid, :gid, :mtime, :checksum, :typeflag, :linkname, :magic, :version,
40
+ :uname, :gname, :devmajor, :devminor
41
+ ].freeze
42
+
43
+ # All fields available in a POSIX tar(1) header.
44
+ FIELDS = (REQUIRED_FIELDS + OPTIONAL_FIELDS).freeze
45
+
46
+ FIELDS.each do |f|
47
+ attr_reader f.to_sym unless f.to_sym == :name
48
+ end
49
+
50
+ # The name of the file. By default, limited to 100 bytes. Required. May be
51
+ # longer (up to BLOCK_SIZE bytes) if using the GNU long name tar extension.
52
+ attr_accessor :name
53
+
54
+ # The pack format passed to Array#pack for encoding a header.
55
+ HEADER_PACK_FORMAT = "a100a8a8a8a12a12a7aaa100a6a2a32a32a8a8a155".freeze
56
+ # The unpack format passed to String#unpack for decoding a header.
57
+ HEADER_UNPACK_FORMAT = "Z100A8A8A8A12A12A8aZ100A6A2Z32Z32A8A8Z155".freeze
58
+
59
+ class << self
60
+ # Creates a new PosixHeader from a data stream.
61
+ def from_stream(stream)
62
+ from_data(stream.read(BLOCK_SIZE))
63
+ end
64
+
65
+ # Creates a new PosixHeader from a data stream. Deprecated; use
66
+ # PosixHeader.from_stream instead.
67
+ def new_from_stream(stream)
68
+ warn "#{__method__} has been deprecated; use from_stream instead."
69
+ from_stream(stream)
70
+ end
71
+
72
+ # Creates a new PosixHeader from a BLOCK_SIZE-byte data buffer.
73
+ def from_data(data)
74
+ fields = data.unpack(HEADER_UNPACK_FORMAT)
75
+ name = fields.shift
76
+ mode = fields.shift.oct
77
+ uid = fields.shift.oct
78
+ gid = fields.shift.oct
79
+ size = strict_oct(fields.shift)
80
+ mtime = fields.shift.oct
81
+ checksum = fields.shift.oct
82
+ typeflag = fields.shift
83
+ linkname = fields.shift
84
+ magic = fields.shift
85
+ version = fields.shift.oct
86
+ uname = fields.shift
87
+ gname = fields.shift
88
+ devmajor = fields.shift.oct
89
+ devminor = fields.shift.oct
90
+ prefix = fields.shift
91
+
92
+ empty = !data.each_byte.any?(&:nonzero?)
93
+
94
+ new(
95
+ name: name,
96
+ mode: mode,
97
+ uid: uid,
98
+ gid: gid,
99
+ size: size,
100
+ mtime: mtime,
101
+ checksum: checksum,
102
+ typeflag: typeflag,
103
+ magic: magic,
104
+ version: version,
105
+ uname: uname,
106
+ gname: gname,
107
+ devmajor: devmajor,
108
+ devminor: devminor,
109
+ prefix: prefix,
110
+ empty: empty,
111
+ linkname: linkname
112
+ )
113
+ end
114
+
115
+ private
116
+
117
+ def strict_oct(string)
118
+ return string.oct if /\A[0-7 ]*\z/.match?(string)
119
+ raise ArgumentError, "#{string.inspect} is not a valid octal string"
120
+ end
121
+ end
122
+
123
+ # Creates a new PosixHeader. A PosixHeader cannot be created unless
124
+ # +name+, +size+, +prefix+, and +mode+ are provided.
125
+ def initialize(v)
126
+ REQUIRED_FIELDS.each do |f|
127
+ raise ArgumentError, "Field #{f} is required." unless v.key?(f)
128
+ end
129
+
130
+ v[:mtime] = v[:mtime].to_i
131
+ v[:checksum] ||= ""
132
+ v[:typeflag] ||= "0"
133
+ v[:magic] ||= MAGIC_BYTES
134
+ v[:version] ||= "00"
135
+
136
+ FIELDS.each do |f|
137
+ instance_variable_set(:"@#{f}", v[f])
138
+ end
139
+
140
+ @empty = v[:empty]
141
+ end
142
+
143
+ # Indicates if the header was an empty header.
144
+ def empty?
145
+ @empty
146
+ end
147
+
148
+ # Indicates if the header has a valid magic value.
149
+ def valid?
150
+ empty? || @magic == MAGIC_BYTES
151
+ end
152
+
153
+ # Returns +true+ if the header is a long name special header which indicates
154
+ # that the next block of data is the filename.
155
+ def long_name?
156
+ typeflag == "L" && name == GNU_EXT_LONG_LINK
157
+ end
158
+
159
+ # A string representation of the header.
160
+ def to_s
161
+ update_checksum
162
+ header(@checksum)
163
+ end
164
+ alias_method :to_str, :to_s
165
+
166
+ # Update the checksum field.
167
+ def update_checksum
168
+ hh = header(" " * 8)
169
+ @checksum = oct(calculate_checksum(hh), 6)
170
+ end
171
+
172
+ private
173
+
174
+ def oct(num, len)
175
+ if num.nil?
176
+ "\0" * (len + 1)
177
+ else
178
+ "%0#{len}o" % num
179
+ end
180
+ end
181
+
182
+ def calculate_checksum(hdr)
183
+ hdr.unpack("C*").inject { |a, e| a + e }
184
+ end
185
+
186
+ def header(chksum)
187
+ arr = [name, oct(mode, 7), oct(uid, 7), oct(gid, 7), oct(size, 11),
188
+ oct(mtime, 11), chksum, " ", typeflag, linkname, magic, version,
189
+ uname, gname, oct(devmajor, 7), oct(devminor, 7), prefix]
190
+ str = arr.pack(HEADER_PACK_FORMAT)
191
+ str + "\0" * ((BLOCK_SIZE - str.bytesize) % BLOCK_SIZE)
192
+ end
193
+
194
+ ##
195
+ # :attr_reader: size
196
+ # The size of the file. Required.
197
+
198
+ ##
199
+ # :attr_reader: prefix
200
+ # The prefix of the file; the path before #name. Limited to 155 bytes.
201
+ # Required.
202
+
203
+ ##
204
+ # :attr_reader: mode
205
+ # The Unix file mode of the file. Stored as an octal integer. Required.
206
+
207
+ ##
208
+ # :attr_reader: uid
209
+ # The Unix owner user ID of the file. Stored as an octal integer.
210
+
211
+ ##
212
+ # :attr_reader: uname
213
+ # The user name of the Unix owner of the file.
214
+
215
+ ##
216
+ # :attr_reader: gid
217
+ # The Unix owner group ID of the file. Stored as an octal integer.
218
+
219
+ ##
220
+ # :attr_reader: gname
221
+ # The group name of the Unix owner of the file.
222
+
223
+ ##
224
+ # :attr_reader: mtime
225
+ # The modification time of the file in epoch seconds. Stored as an
226
+ # octal integer.
227
+
228
+ ##
229
+ # :attr_reader: checksum
230
+ # The checksum of the file. Stored as an octal integer. Calculated
231
+ # before encoding the header as a string.
232
+
233
+ ##
234
+ # :attr_reader: typeflag
235
+ # The type of record in the file.
236
+ #
237
+ # +0+:: Regular file. NULL should be treated as a synonym, for compatibility
238
+ # purposes.
239
+ # +1+:: Hard link.
240
+ # +2+:: Symbolic link.
241
+ # +3+:: Character device node.
242
+ # +4+:: Block device node.
243
+ # +5+:: Directory.
244
+ # +6+:: FIFO node.
245
+ # +7+:: Reserved.
246
+
247
+ ##
248
+ # :attr_reader: linkname
249
+ # The name of the link stored. Not currently used.
250
+
251
+ ##
252
+ # :attr_reader: magic
253
+ # Always "ustar\0".
254
+
255
+ ##
256
+ # :attr_reader: version
257
+ # Always "00"
258
+
259
+ ##
260
+ # :attr_reader: devmajor
261
+ # The major device ID. Not currently used.
262
+
263
+ ##
264
+ # :attr_reader: devminor
265
+ # The minor device ID. Not currently used.
266
+ end
267
+ end
@@ -1,12 +1,9 @@
1
- # coding: utf-8
2
-
3
- module Archive::Tar::Minitar
1
+ class Minitar
4
2
  # The class that reads a tar format archive from a data stream. The data
5
3
  # stream may be sequential or random access, but certain features only work
6
4
  # with random access data streams.
7
5
  class Reader
8
6
  include Enumerable
9
- include Archive::Tar::Minitar::ByteSize
10
7
 
11
8
  # This marks the EntryStream closed for reading without closing the
12
9
  # actual data stream.
@@ -30,9 +27,7 @@ module Archive::Tar::Minitar
30
27
 
31
28
  # EntryStreams are pseudo-streams on top of the main data stream.
32
29
  class EntryStream
33
- include Archive::Tar::Minitar::ByteSize
34
-
35
- Archive::Tar::Minitar::PosixHeader::FIELDS.each do |field|
30
+ Minitar::PosixHeader::FIELDS.each do |field|
36
31
  attr_reader field.to_sym
37
32
  end
38
33
 
@@ -56,7 +51,7 @@ module Archive::Tar::Minitar
56
51
  @prefix = header.prefix
57
52
  @read = 0
58
53
  @orig_pos =
59
- if Archive::Tar::Minitar.seekable?(@io)
54
+ if Minitar.seekable?(@io)
60
55
  @io.pos
61
56
  else
62
57
  0
@@ -70,7 +65,7 @@ module Archive::Tar::Minitar
70
65
  len ||= @size - @read
71
66
  max_read = [len, @size - @read].min
72
67
  ret = @io.read(max_read)
73
- @read += bytesize(ret)
68
+ @read += ret.bytesize
74
69
  ret
75
70
  end
76
71
 
@@ -119,8 +114,8 @@ module Archive::Tar::Minitar
119
114
 
120
115
  # Sets the current read pointer to the beginning of the EntryStream.
121
116
  def rewind
122
- unless Archive::Tar::Minitar.seekable?(@io, :pos=)
123
- raise Archive::Tar::Minitar::NonSeekableStream
117
+ unless Minitar.seekable?(@io, :pos=)
118
+ raise Minitar::NonSeekableStream
124
119
  end
125
120
  @io.pos = @orig_pos
126
121
  @read = 0
@@ -177,7 +172,7 @@ module Archive::Tar::Minitar
177
172
  # Iterates over each entry in the provided input. This wraps the common
178
173
  # pattern of:
179
174
  #
180
- # Archive::Tar::Minitar::Input.open(io) do |i|
175
+ # Minitar::Input.open(io) do |i|
181
176
  # inp.each do |entry|
182
177
  # # ...
183
178
  # end
@@ -187,8 +182,8 @@ module Archive::Tar::Minitar
187
182
  # behaviour.
188
183
  #
189
184
  # call-seq:
190
- # Archive::Tar::Minitar::Reader.each_entry(io) -> enumerator
191
- # Archive::Tar::Minitar::Reader.each_entry(io) { |entry| block } -> obj
185
+ # Minitar::Reader.each_entry(io) -> enumerator
186
+ # Minitar::Reader.each_entry(io) { |entry| block } -> obj
192
187
  def self.each_entry(io)
193
188
  return to_enum(__method__, io) unless block_given?
194
189
 
@@ -214,13 +209,13 @@ module Archive::Tar::Minitar
214
209
  # random access data streams that respond to #rewind and #pos.
215
210
  def rewind
216
211
  if @init_pos.zero?
217
- unless Archive::Tar::Minitar.seekable?(@io, :rewind)
218
- raise Archive::Tar::Minitar::NonSeekableStream
212
+ unless Minitar.seekable?(@io, :rewind)
213
+ raise Minitar::NonSeekableStream
219
214
  end
220
215
  @io.rewind
221
216
  else
222
- unless Archive::Tar::Minitar.seekable?(@io, :pos=)
223
- raise Archive::Tar::Minitar::NonSeekableStream
217
+ unless Minitar.seekable?(@io, :pos=)
218
+ raise Minitar::NonSeekableStream
224
219
  end
225
220
  @io.pos = @init_pos
226
221
  end
@@ -233,11 +228,11 @@ module Archive::Tar::Minitar
233
228
  loop do
234
229
  return if @io.eof?
235
230
 
236
- header = Archive::Tar::Minitar::PosixHeader.from_stream(@io)
237
- raise Archive::Tar::Minitar::InvalidTarStream unless header.valid?
231
+ header = Minitar::PosixHeader.from_stream(@io)
232
+ raise Minitar::InvalidTarStream unless header.valid?
238
233
  return if header.empty?
239
234
 
240
- raise Archive::Tar::Minitar::InvalidTarStream if header.size < 0
235
+ raise Minitar::InvalidTarStream if header.size < 0
241
236
 
242
237
  if header.long_name?
243
238
  name_block = (header.size / 512.0).ceil * 512
@@ -256,13 +251,13 @@ module Archive::Tar::Minitar
256
251
 
257
252
  skip = (512 - (size % 512)) % 512
258
253
 
259
- if Archive::Tar::Minitar.seekable?(@io, :seek)
254
+ if Minitar.seekable?(@io, :seek)
260
255
  # avoid reading...
261
256
  @io.seek(size - entry.bytes_read, IO::SEEK_CUR)
262
257
  else
263
258
  pending = size - entry.bytes_read
264
259
  while pending > 0
265
- bread = bytesize(@io.read([pending, 4096].min))
260
+ bread = @io.read([pending, 4096].min).bytesize
266
261
  raise UnexpectedEOF if @io.eof?
267
262
  pending -= bread
268
263
  end
@@ -1,10 +1,6 @@
1
- # coding: utf-8
2
-
3
- module Archive::Tar::Minitar
1
+ class Minitar
4
2
  # The class that writes a tar format archive to a data stream.
5
3
  class Writer
6
- include Archive::Tar::Minitar::ByteSize
7
-
8
4
  # The exception raised when the user attempts to write more data to a
9
5
  # BoundedWriteStream than has been allocated.
10
6
  WriteBoundaryOverflow = Class.new(StandardError)
@@ -25,15 +21,13 @@ module Archive::Tar::Minitar
25
21
 
26
22
  # A WriteOnlyStream that also has a size limit.
27
23
  class BoundedWriteStream < WriteOnlyStream
28
- include Archive::Tar::Minitar::ByteSize
29
-
30
24
  def self.const_missing(c)
31
25
  case c
32
26
  when :FileOverflow
33
27
  warn "Writer::BoundedWriteStream::FileOverflow has been renamed " \
34
28
  "to Writer::WriteBoundaryOverflow"
35
29
  const_set :FileOverflow,
36
- Archive::Tar::Minitar::Writer::WriteBoundaryOverflow
30
+ Minitar::Writer::WriteBoundaryOverflow
37
31
  else
38
32
  super
39
33
  end
@@ -52,7 +46,7 @@ module Archive::Tar::Minitar
52
46
  end
53
47
 
54
48
  def write(data)
55
- size = bytesize(data)
49
+ size = data.bytesize
56
50
  raise WriteBoundaryOverflow if (size + @written) > @limit
57
51
  @io.write(data)
58
52
  @written += size
@@ -79,11 +73,11 @@ module Archive::Tar::Minitar
79
73
  # of the block.
80
74
  #
81
75
  # call-seq:
82
- # w = Archive::Tar::Minitar::Writer.open(STDOUT)
76
+ # w = Minitar::Writer.open(STDOUT)
83
77
  # w.add_file_simple('foo.txt', :size => 3)
84
78
  # w.close
85
79
  #
86
- # Archive::Tar::Minitar::Writer.open(STDOUT) do |w|
80
+ # Minitar::Writer.open(STDOUT) do |w|
87
81
  # w.add_file_simple('foo.txt', :size => 3)
88
82
  # end
89
83
  def self.open(io) # :yields Writer:
@@ -139,10 +133,10 @@ module Archive::Tar::Minitar
139
133
  raise ClosedStream if @closed
140
134
 
141
135
  header = {
142
- :mode => opts.fetch(:mode, 0o644),
143
- :mtime => opts.fetch(:mtime, nil),
144
- :gid => opts.fetch(:gid, nil),
145
- :uid => opts.fetch(:uid, nil)
136
+ mode: opts.fetch(:mode, 0o644),
137
+ mtime: opts.fetch(:mtime, nil),
138
+ gid: opts.fetch(:gid, nil),
139
+ uid: opts.fetch(:uid, nil)
146
140
  }
147
141
 
148
142
  data = opts.fetch(:data, nil)
@@ -158,7 +152,7 @@ module Archive::Tar::Minitar
158
152
  else
159
153
  raise ArgumentError, "No data provided" unless data
160
154
 
161
- bytes = bytesize(data)
155
+ bytes = data.bytesize
162
156
  size = bytes if size.nil? || size < bytes
163
157
  end
164
158
 
@@ -203,13 +197,13 @@ module Archive::Tar::Minitar
203
197
  # #add_file_simple must be used.
204
198
  #
205
199
  # +opts+ may be modified during the writing of the file to the stream.
206
- def add_file(name, opts = {}, &block) # :yields WriteOnlyStream, +opts+:
200
+ def add_file(name, opts = {}, &) # :yields WriteOnlyStream, +opts+:
207
201
  raise ClosedStream if @closed
208
202
 
209
- return add_file_simple(name, opts, &block) if opts[:data]
203
+ return add_file_simple(name, opts, &) if opts[:data]
210
204
 
211
- unless Archive::Tar::Minitar.seekable?(@io)
212
- raise Archive::Tar::Minitar::NonSeekableStream
205
+ unless Minitar.seekable?(@io)
206
+ raise Minitar::NonSeekableStream
213
207
  end
214
208
 
215
209
  short_name, prefix, needs_long_name = split_name(name)
@@ -227,11 +221,11 @@ module Archive::Tar::Minitar
227
221
  final_pos, @io.pos = @io.pos, init_pos
228
222
 
229
223
  header = {
230
- :mode => opts[:mode],
231
- :mtime => opts[:mtime],
232
- :size => size,
233
- :gid => opts[:gid],
234
- :uid => opts[:uid]
224
+ mode: opts[:mode],
225
+ mtime: opts[:mtime],
226
+ size: size,
227
+ gid: opts[:gid],
228
+ uid: opts[:uid]
235
229
  }
236
230
 
237
231
  write_header(header, name, short_name, prefix, needs_long_name)
@@ -244,12 +238,12 @@ module Archive::Tar::Minitar
244
238
  raise ClosedStream if @closed
245
239
 
246
240
  header = {
247
- :mode => opts[:mode],
248
- :typeflag => "5",
249
- :size => 0,
250
- :gid => opts[:gid],
251
- :uid => opts[:uid],
252
- :mtime => opts[:mtime]
241
+ mode: opts[:mode],
242
+ typeflag: "5",
243
+ size: 0,
244
+ gid: opts[:gid],
245
+ uid: opts[:uid],
246
+ mtime: opts[:mtime]
253
247
  }
254
248
 
255
249
  short_name, prefix, needs_long_name = split_name(name)
@@ -266,15 +260,15 @@ module Archive::Tar::Minitar
266
260
 
267
261
  name, prefix = split_name(name)
268
262
  header = {
269
- :name => name,
270
- :mode => opts[:mode],
271
- :typeflag => "2",
272
- :size => 0,
273
- :linkname => link_target,
274
- :gid => opts[:gid],
275
- :uid => opts[:uid],
276
- :mtime => opts[:mtime],
277
- :prefix => prefix
263
+ name: name,
264
+ mode: opts[:mode],
265
+ typeflag: "2",
266
+ size: 0,
267
+ linkname: link_target,
268
+ gid: opts[:gid],
269
+ uid: opts[:uid],
270
+ mtime: opts[:mtime],
271
+ prefix: prefix
278
272
  }
279
273
  @io.write(PosixHeader.new(header))
280
274
  nil
@@ -305,23 +299,23 @@ module Archive::Tar::Minitar
305
299
  def write_header(header, long_name, short_name, prefix, needs_long_name)
306
300
  if needs_long_name
307
301
  long_name_header = {
308
- :prefix => "",
309
- :name => PosixHeader::GNU_EXT_LONG_LINK,
310
- :typeflag => "L",
311
- :size => long_name.length + 1,
312
- :mode => 0
302
+ prefix: "",
303
+ name: PosixHeader::GNU_EXT_LONG_LINK,
304
+ typeflag: "L",
305
+ size: long_name.length + 1,
306
+ mode: 0
313
307
  }
314
308
  @io.write(PosixHeader.new(long_name_header))
315
309
  @io.write(long_name)
316
310
  @io.write("\0" * (512 - (long_name.length % 512)))
317
311
  end
318
312
 
319
- new_header = header.merge({:name => short_name, :prefix => prefix})
313
+ new_header = header.merge({name: short_name, prefix: prefix})
320
314
  @io.write(PosixHeader.new(new_header))
321
315
  end
322
316
 
323
317
  def split_name(name)
324
- if bytesize(name) <= 100
318
+ if name.bytesize <= 100
325
319
  prefix = ""
326
320
  else
327
321
  parts = name.split("/")
@@ -331,7 +325,7 @@ module Archive::Tar::Minitar
331
325
 
332
326
  loop do
333
327
  nxt = parts.pop || ""
334
- break if bytesize(newname) + 1 + bytesize(nxt) >= 100
328
+ break if newname.bytesize + 1 + nxt.bytesize >= 100
335
329
  newname = "#{nxt}/#{newname}"
336
330
  end
337
331
 
@@ -340,7 +334,7 @@ module Archive::Tar::Minitar
340
334
  name = newname
341
335
  end
342
336
 
343
- [name, prefix, bytesize(name) > 100 || bytesize(prefix) > 155]
337
+ [name, prefix, name.bytesize > 100 || prefix.bytesize > 155]
344
338
  end
345
339
  end
346
340
  end