sys-filesystem 1.4.3 → 1.5.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  ####################################################################
2
4
  # sys_filesystem_unix_spec.rb
3
5
  #
@@ -8,389 +10,732 @@ require 'spec_helper'
8
10
  require 'sys-filesystem'
9
11
  require 'pathname'
10
12
 
11
- RSpec.describe Sys::Filesystem, :unix => true do
12
- let(:solaris) { RbConfig::CONFIG['host_os'] =~ /sunos|solaris/i }
13
+ RSpec.describe Sys::Filesystem, :unix do
13
14
  let(:linux) { RbConfig::CONFIG['host_os'] =~ /linux/i }
14
- let(:bsd) { RbConfig::CONFIG['host_os'] =~ /bsd/i }
15
+ let(:bsd) { RbConfig::CONFIG['host_os'] =~ /bsd|dragonfly/i }
15
16
  let(:darwin) { RbConfig::CONFIG['host_os'] =~ /mac|darwin/i }
16
17
  let(:root) { '/' }
17
18
 
18
19
  before do
19
- @stat = Sys::Filesystem.stat(root)
20
+ @stat = described_class.stat(root)
20
21
  @size = 58720256
21
22
  end
22
23
 
23
- example "version number is set to the expected value" do
24
- expect(Sys::Filesystem::VERSION).to eq('1.4.3')
25
- expect(Sys::Filesystem::VERSION).to be_frozen
26
- end
27
-
28
- example "you cannot instantiate an instance" do
29
- expect{ described_class.new }.to raise_error(NoMethodError)
30
- end
31
-
32
- example "stat path works as expected" do
24
+ example 'stat path works as expected' do
33
25
  expect(@stat).to respond_to(:path)
34
26
  expect(@stat.path).to eq(root)
35
27
  end
36
28
 
37
- example "stat block_size works as expected" do
29
+ example 'stat block_size works as expected' do
38
30
  expect(@stat).to respond_to(:block_size)
39
- expect(@stat.block_size).to be_kind_of(Numeric)
31
+ expect(@stat.block_size).to be_a(Numeric)
40
32
  end
41
33
 
42
- example "stat fragment_size works as expected" do
34
+ example 'stat fragment_size works as expected' do
43
35
  expect(@stat).to respond_to(:fragment_size)
44
- expect(@stat.fragment_size).to be_kind_of(Numeric)
36
+ expect(@stat.fragment_size).to be_a(Numeric)
45
37
  end
46
38
 
47
- example "stat fragment_size is a plausible value" do
39
+ example 'stat fragment_size is a plausible value' do
48
40
  expect(@stat.fragment_size).to be >= 512
49
- expect(@stat.fragment_size).to be <= 16384
41
+ expect(@stat.fragment_size).to be <= 2**16
42
+ expect(@stat.fragment_size).to be <= @stat.block_size
50
43
  end
51
44
 
52
- example "stat blocks works as expected" do
45
+ example 'stat blocks works as expected' do
53
46
  expect(@stat).to respond_to(:blocks)
54
- expect(@stat.blocks).to be_kind_of(Numeric)
47
+ expect(@stat.blocks).to be_a(Numeric)
55
48
  end
56
49
 
57
- example "stat blocks_free works as expected" do
50
+ example 'stat blocks_free works as expected' do
58
51
  expect(@stat).to respond_to(:blocks_free)
59
- expect(@stat.blocks_free).to be_kind_of(Numeric)
52
+ expect(@stat.blocks_free).to be_a(Numeric)
60
53
  end
61
54
 
62
- example "stat blocks_available works as expected" do
55
+ example 'stat blocks_available works as expected' do
63
56
  expect(@stat).to respond_to(:blocks_available)
64
- expect(@stat.blocks_available).to be_kind_of(Numeric)
57
+ expect(@stat.blocks_available).to be_a(Numeric)
65
58
  end
66
59
 
67
- example "stat files works as expected" do
60
+ example 'stat files works as expected' do
68
61
  expect(@stat).to respond_to(:files)
69
- expect(@stat.files).to be_kind_of(Numeric)
62
+ expect(@stat.files).to be_a(Numeric)
70
63
  end
71
64
 
72
- example "stat inodes is an alias for files" do
65
+ example 'stat inodes is an alias for files' do
73
66
  expect(@stat).to respond_to(:inodes)
74
67
  expect(@stat.method(:inodes)).to eq(@stat.method(:files))
75
68
  end
76
69
 
77
- example "stat files tree works as expected" do
70
+ example 'stat files tree works as expected' do
78
71
  expect(@stat).to respond_to(:files_free)
79
- expect(@stat.files_free).to be_kind_of(Numeric)
72
+ expect(@stat.files_free).to be_a(Numeric)
80
73
  end
81
74
 
82
- example "stat inodes_free is an alias for files_free" do
75
+ example 'stat inodes_free is an alias for files_free' do
83
76
  expect(@stat).to respond_to(:inodes_free)
84
77
  expect(@stat.method(:inodes_free)).to eq(@stat.method(:files_free))
85
78
  end
86
79
 
87
- example "stat files_available works as expected" do
80
+ example 'stat files_available works as expected' do
88
81
  expect(@stat).to respond_to(:files_available)
89
- expect(@stat.files_available).to be_kind_of(Numeric)
82
+ expect(@stat.files_available).to be_a(Numeric)
90
83
  end
91
84
 
92
- example "stat inodes_available is an alias for files_available" do
85
+ example 'stat inodes_available is an alias for files_available' do
93
86
  expect(@stat).to respond_to(:inodes_available)
94
87
  expect(@stat.method(:inodes_available)).to eq(@stat.method(:files_available))
95
88
  end
96
89
 
97
- example "stat filesystem_id works as expected" do
90
+ example 'stat filesystem_id works as expected' do
98
91
  expect(@stat).to respond_to(:filesystem_id)
99
- expect(@stat.filesystem_id).to be_kind_of(Integer)
92
+ expect(@stat.filesystem_id).to be_a(Integer)
100
93
  end
101
94
 
102
- example "stat flags works as expected" do
95
+ example 'stat flags works as expected' do
103
96
  expect(@stat).to respond_to(:flags)
104
- expect(@stat.flags).to be_kind_of(Numeric)
97
+ expect(@stat.flags).to be_a(Numeric)
105
98
  end
106
99
 
107
- example "stat name_max works as expected" do
100
+ example 'stat name_max works as expected' do
108
101
  expect(@stat).to respond_to(:name_max)
109
- expect(@stat.name_max).to be_kind_of(Numeric)
102
+ expect(@stat.name_max).to be_a(Numeric)
110
103
  end
111
104
 
112
- example "stat base_type works as expected" do
113
- skip "base_type test skipped except on Solaris" unless solaris
105
+ context 'dragonfly', :dragonfly do
106
+ example 'owner works as expected' do
107
+ expect(@stat).to respond_to(:owner)
108
+ expect(@stat.owner).to be_a(Numeric)
109
+ end
110
+
111
+ example 'filesystem_type works as expected' do
112
+ expect(@stat).to respond_to(:filesystem_type)
113
+ expect(@stat.filesystem_type).to be_a(Numeric)
114
+ end
115
+
116
+ example 'sync_reads works as expected' do
117
+ expect(@stat).to respond_to(:sync_reads)
118
+ expect(@stat.sync_reads).to be_a(Numeric)
119
+ end
114
120
 
115
- expect(@stat).to respond_to(:base_type)
116
- expect(@stat.base_type).to be_kind_of(String)
121
+ example 'async_reads works as expected' do
122
+ expect(@stat).to respond_to(:async_reads)
123
+ expect(@stat.async_reads).to be_a(Numeric)
124
+ end
125
+
126
+ example 'sync_writes works as expected' do
127
+ expect(@stat).to respond_to(:sync_writes)
128
+ expect(@stat.sync_writes).to be_a(Numeric)
129
+ end
130
+
131
+ example 'async_writes works as expected' do
132
+ expect(@stat).to respond_to(:async_writes)
133
+ expect(@stat.async_writes).to be_a(Numeric)
134
+ end
117
135
  end
118
136
 
119
- example "stat constants are defined" do
137
+ example 'stat constants are defined' do
120
138
  expect(Sys::Filesystem::Stat::RDONLY).not_to be_nil
121
139
  expect(Sys::Filesystem::Stat::NOSUID).not_to be_nil
122
140
  end
123
141
 
124
- example "stat constants for solaris are defined" do
125
- skip "NOTRUNC test skipped except on Solaris" unless solaris
126
- expect(Sys::Filesystem::Stat::NOTRUNC).not_to be_nil
127
- end
128
-
129
- example "stat bytes_total works as expected" do
142
+ example 'stat bytes_total works as expected' do
130
143
  expect(@stat).to respond_to(:bytes_total)
131
- expect(@stat.bytes_total).to be_kind_of(Numeric)
144
+ expect(@stat.bytes_total).to be_a(Numeric)
132
145
  end
133
146
 
134
- example "stat bytes_free works as expected" do
147
+ example 'stat bytes_free works as expected' do
135
148
  expect(@stat).to respond_to(:bytes_free)
136
- expect(@stat.bytes_free).to be_kind_of(Numeric)
149
+ expect(@stat.bytes_free).to be_a(Numeric)
137
150
  expect(@stat.blocks_free * @stat.fragment_size).to eq(@stat.bytes_free)
138
151
  end
139
152
 
140
- example "stat bytes_available works as expected" do
153
+ example 'stat bytes_available works as expected' do
141
154
  expect(@stat).to respond_to(:bytes_available)
142
- expect(@stat.bytes_available).to be_kind_of(Numeric)
155
+ expect(@stat.bytes_available).to be_a(Numeric)
143
156
  expect(@stat.blocks_available * @stat.fragment_size).to eq(@stat.bytes_available)
144
157
  end
145
158
 
146
- example "stat bytes works as expected" do
159
+ example 'stat bytes works as expected' do
147
160
  expect(@stat).to respond_to(:bytes_used)
148
- expect(@stat.bytes_used).to be_kind_of(Numeric)
161
+ expect(@stat.bytes_used).to be_a(Numeric)
149
162
  end
150
163
 
151
- example "stat percent_used works as expected" do
164
+ example 'stat percent_used works as expected' do
152
165
  expect(@stat).to respond_to(:percent_used)
153
- expect(@stat.percent_used).to be_kind_of(Float)
166
+ expect(@stat.percent_used).to be_a(Float)
154
167
  end
155
168
 
156
- example "stat singleton method requires an argument" do
157
- expect{ Sys::Filesystem.stat }.to raise_error(ArgumentError)
169
+ example 'stat singleton method requires an argument' do
170
+ expect{ described_class.stat }.to raise_error(ArgumentError)
158
171
  end
159
172
 
160
- example "stat case_insensitive method works as expected" do
173
+ example 'stat case_insensitive method works as expected' do
161
174
  expected = darwin ? true : false
162
175
  expect(@stat.case_insensitive?).to eq(expected)
163
- expect(Sys::Filesystem.stat(Dir.home).case_insensitive?).to eq(expected)
176
+ expect(described_class.stat(Dir.home).case_insensitive?).to eq(expected)
164
177
  end
165
178
 
166
- example "stat case_sensitive method works as expected" do
179
+ example 'stat case_sensitive method works as expected' do
167
180
  expected = darwin ? false : true
168
181
  expect(@stat.case_sensitive?).to eq(expected)
169
- expect(Sys::Filesystem.stat(Dir.home).case_sensitive?).to eq(expected)
182
+ expect(described_class.stat(Dir.home).case_sensitive?).to eq(expected)
170
183
  end
171
184
 
172
- example "numeric helper methods are defined" do
185
+ example 'numeric helper methods are defined' do
173
186
  expect(@size).to respond_to(:to_kb)
174
187
  expect(@size).to respond_to(:to_mb)
175
188
  expect(@size).to respond_to(:to_gb)
176
189
  expect(@size).to respond_to(:to_tb)
177
190
  end
178
191
 
179
- example "to_kb works as expected" do
192
+ example 'to_kb works as expected' do
180
193
  expect(@size.to_kb).to eq(57344)
181
194
  end
182
195
 
183
- example "to_mb works as expected" do
196
+ example 'to_mb works as expected' do
184
197
  expect(@size.to_mb).to eq(56)
185
198
  end
186
199
 
187
- example "to_gb works as expected" do
200
+ example 'to_gb works as expected' do
188
201
  expect(@size.to_gb).to eq(0)
189
202
  end
190
203
 
191
- context "Filesystem.stat(Pathname)" do
204
+ context 'Filesystem.stat(Pathname)' do
192
205
  before do
193
- @stat_pathname = Sys::Filesystem.stat(Pathname.new(root))
206
+ @stat_pathname = described_class.stat(Pathname.new(root))
194
207
  end
195
208
 
196
- example "stat with Pathname argument works as expected" do
209
+ example 'class returns expected value with pathname argument' do
197
210
  expect(@stat_pathname.class).to eq(@stat.class)
211
+ end
212
+
213
+ example 'path returns expected value with pathname argument' do
198
214
  expect(@stat_pathname.path).to eq(@stat.path)
215
+ end
216
+
217
+ example 'block_size returns expected value with pathname argument' do
199
218
  expect(@stat_pathname.block_size).to eq(@stat.block_size)
219
+ end
220
+
221
+ example 'fragment_size returns expected value with pathname argument' do
200
222
  expect(@stat_pathname.fragment_size).to eq(@stat.fragment_size)
223
+ end
224
+
225
+ example 'blocks returns expected value with pathname argument' do
201
226
  expect(@stat_pathname.blocks).to eq(@stat.blocks)
227
+ end
228
+
229
+ example 'blocks_free returns expected value with pathname argument' do
202
230
  expect(@stat_pathname.blocks_free).to eq(@stat.blocks_free)
231
+ end
232
+
233
+ example 'blocks_available returns expected value with pathname argument' do
203
234
  expect(@stat_pathname.blocks_available).to eq(@stat.blocks_available)
235
+ end
236
+
237
+ example 'files returns expected value with pathname argument' do
204
238
  expect(@stat_pathname.files).to eq(@stat.files)
239
+ end
240
+
241
+ example 'files_free returns expected value with pathname argument' do
205
242
  expect(@stat_pathname.files_free).to eq(@stat.files_free)
243
+ end
244
+
245
+ example 'files_available returns expected value with pathname argument' do
206
246
  expect(@stat_pathname.files_available).to eq(@stat.files_available)
247
+ end
248
+
249
+ example 'filesystem_id returns expected value with pathname argument' do
207
250
  expect(@stat_pathname.filesystem_id).to eq(@stat.filesystem_id)
251
+ end
252
+
253
+ example 'flags returns expected value with pathname argument' do
208
254
  expect(@stat_pathname.flags).to eq(@stat.flags)
255
+ end
256
+
257
+ example 'name_max returns expected value with pathname argument' do
209
258
  expect(@stat_pathname.name_max).to eq(@stat.name_max)
259
+ end
260
+
261
+ example 'base_type returns expected value with pathname argument' do
210
262
  expect(@stat_pathname.base_type).to eq(@stat.base_type)
211
263
  end
212
264
  end
213
265
 
214
- context "Filesystem.stat(File)" do
266
+ context 'Filesystem.stat(File)' do
215
267
  before do
216
- @stat_file = File.open(root){ |file| Sys::Filesystem.stat(file) }
268
+ @stat_file = File.open(root){ |file| described_class.stat(file) }
217
269
  end
218
270
 
219
- example "stat with File argument works as expected" do
271
+ example 'class returns expected value with file argument' do
220
272
  expect(@stat_file.class).to eq(@stat.class)
273
+ end
274
+
275
+ example 'path returns expected value with file argument' do
221
276
  expect(@stat_file.path).to eq(@stat.path)
277
+ end
278
+
279
+ example 'block_size returns expected value with file argument' do
222
280
  expect(@stat_file.block_size).to eq(@stat.block_size)
281
+ end
282
+
283
+ example 'fragment_size returns expected value with file argument' do
223
284
  expect(@stat_file.fragment_size).to eq(@stat.fragment_size)
285
+ end
286
+
287
+ example 'blocks returns expected value with file argument' do
224
288
  expect(@stat_file.blocks).to eq(@stat.blocks)
289
+ end
290
+
291
+ example 'blocks_free returns expected value with file argument' do
225
292
  expect(@stat_file.blocks_free).to eq(@stat.blocks_free)
293
+ end
294
+
295
+ example 'blocks_available returns expected value with file argument' do
226
296
  expect(@stat_file.blocks_available).to eq(@stat.blocks_available)
297
+ end
298
+
299
+ example 'files returns expected value with file argument' do
227
300
  expect(@stat_file.files).to eq(@stat.files)
301
+ end
302
+
303
+ example 'files_free returns expected value with file argument' do
228
304
  expect(@stat_file.files_free).to eq(@stat.files_free)
305
+ end
306
+
307
+ example 'files_available returns expected value with file argument' do
229
308
  expect(@stat_file.files_available).to eq(@stat.files_available)
309
+ end
310
+
311
+ example 'filesystem_id returns expected value with file argument' do
230
312
  expect(@stat_file.filesystem_id).to eq(@stat.filesystem_id)
313
+ end
314
+
315
+ example 'flags returns expected value with file argument' do
231
316
  expect(@stat_file.flags).to eq(@stat.flags)
317
+ end
318
+
319
+ example 'name_max returns expected value with file argument' do
232
320
  expect(@stat_file.name_max).to eq(@stat.name_max)
321
+ end
322
+
323
+ example 'base_type returns expected value with file argument' do
233
324
  expect(@stat_file.base_type).to eq(@stat.base_type)
234
325
  end
235
326
  end
236
327
 
237
- context "Filesystem.stat(Dir)" do
328
+ context 'Filesystem.stat(Dir)' do
238
329
  before do
239
- @stat_dir = Dir.open(root){ |dir| Sys::Filesystem.stat(dir) }
330
+ @stat_dir = Dir.open(root){ |dir| described_class.stat(dir) }
240
331
  end
241
332
 
242
- example "stat with Dir argument works as expected" do
333
+ example 'class returns expected value with Dir argument' do
243
334
  expect(@stat_dir.class).to eq(@stat.class)
335
+ end
336
+
337
+ example 'path returns expected value with Dir argument' do
244
338
  expect(@stat_dir.path).to eq(@stat.path)
339
+ end
340
+
341
+ example 'block_size returns expected value with Dir argument' do
245
342
  expect(@stat_dir.block_size).to eq(@stat.block_size)
343
+ end
344
+
345
+ example 'fragment_size returns expected value with Dir argument' do
246
346
  expect(@stat_dir.fragment_size).to eq(@stat.fragment_size)
347
+ end
348
+
349
+ example 'blocks returns expected value with Dir argument' do
247
350
  expect(@stat_dir.blocks).to eq(@stat.blocks)
351
+ end
352
+
353
+ example 'blocks_free returns expected value with Dir argument' do
248
354
  expect(@stat_dir.blocks_free).to eq(@stat.blocks_free)
355
+ end
356
+
357
+ example 'blocks_available returns expected value with Dir argument' do
249
358
  expect(@stat_dir.blocks_available).to eq(@stat.blocks_available)
359
+ end
360
+
361
+ example 'files returns expected value with Dir argument' do
250
362
  expect(@stat_dir.files).to eq(@stat.files)
363
+ end
364
+
365
+ example 'files_free returns expected value with Dir argument' do
251
366
  expect(@stat_dir.files_free).to eq(@stat.files_free)
367
+ end
368
+
369
+ example 'files_available returns expected value with Dir argument' do
252
370
  expect(@stat_dir.files_available).to eq(@stat.files_available)
371
+ end
372
+
373
+ example 'filesystem_id returns expected value with Dir argument' do
253
374
  expect(@stat_dir.filesystem_id).to eq(@stat.filesystem_id)
375
+ end
376
+
377
+ example 'flags returns expected value with Dir argument' do
254
378
  expect(@stat_dir.flags).to eq(@stat.flags)
379
+ end
380
+
381
+ example 'name_max returns expected value with Dir argument' do
255
382
  expect(@stat_dir.name_max).to eq(@stat.name_max)
383
+ end
384
+
385
+ example 'base_type returns expected value with Dir argument' do
256
386
  expect(@stat_dir.base_type).to eq(@stat.base_type)
257
387
  end
258
388
  end
259
389
 
260
- context "Filesystem::Mount" do
261
- let(:mount){ Sys::Filesystem.mounts[0] }
390
+ context 'Filesystem::Mount' do
391
+ let(:mount){ described_class.mounts[0] }
262
392
 
263
393
  before do
264
394
  @array = []
265
395
  end
266
396
 
267
- example "mounts singleton method works as expected without a block" do
268
- expect{ @array = Sys::Filesystem.mounts }.not_to raise_error
269
- expect(@array[0]).to be_kind_of(Sys::Filesystem::Mount)
397
+ example 'mounts singleton method works as expected without a block' do
398
+ expect{ @array = described_class.mounts }.not_to raise_error
399
+ expect(@array[0]).to be_a(Sys::Filesystem::Mount)
270
400
  end
271
401
 
272
- example "mounts singleton method works as expected with a block" do
273
- expect{ Sys::Filesystem.mounts{ |m| @array << m } }.not_to raise_error
274
- expect(@array[0]).to be_kind_of(Sys::Filesystem::Mount)
402
+ example 'mounts singleton method works as expected with a block' do
403
+ expect{ described_class.mounts{ |m| @array << m } }.not_to raise_error
404
+ expect(@array[0]).to be_a(Sys::Filesystem::Mount)
275
405
  end
276
406
 
277
- example "calling the mounts singleton method a large number of times does not cause issues" do
278
- expect{ 1000.times{ @array = Sys::Filesystem.mounts } }.not_to raise_error
407
+ example 'calling the mounts singleton method a large number of times does not cause issues' do
408
+ expect{ 1000.times{ @array = described_class.mounts } }.not_to raise_error
279
409
  end
280
410
 
281
- example "mount name method works as expected" do
411
+ example 'mount name method works as expected' do
282
412
  expect(mount).to respond_to(:name)
283
- expect(mount.name).to be_kind_of(String)
413
+ expect(mount.name).to be_a(String)
284
414
  end
285
415
 
286
- example "mount fsname is an alias for name" do
416
+ example 'mount fsname is an alias for name' do
287
417
  expect(mount).to respond_to(:fsname)
288
418
  expect(mount.method(:fsname)).to eq(mount.method(:name))
289
419
  end
290
420
 
291
- example "mount point method works as expected" do
421
+ example 'mount point method works as expected' do
292
422
  expect(mount).to respond_to(:mount_point)
293
- expect(mount.mount_point).to be_kind_of(String)
423
+ expect(mount.mount_point).to be_a(String)
294
424
  end
295
425
 
296
- example "mount dir is an alias for mount_point" do
426
+ example 'mount dir is an alias for mount_point' do
297
427
  expect(mount).to respond_to(:dir)
298
428
  expect(mount.method(:dir)).to eq(mount.method(:mount_point))
299
429
  end
300
430
 
301
- example "mount mount_type works as expected" do
431
+ example 'mount mount_type works as expected' do
302
432
  expect(mount).to respond_to(:mount_type)
303
- expect(mount.mount_type).to be_kind_of(String)
433
+ expect(mount.mount_type).to be_a(String)
304
434
  end
305
435
 
306
- example "mount options works as expected" do
436
+ example 'mount options works as expected' do
307
437
  expect(mount).to respond_to(:options)
308
- expect(mount.options).to be_kind_of(String)
438
+ expect(mount.options).to be_a(String)
309
439
  end
310
440
 
311
- example "mount opts is an alias for options" do
441
+ example 'mount opts is an alias for options' do
312
442
  expect(mount).to respond_to(:opts)
313
443
  expect(mount.method(:opts)).to eq(mount.method(:options))
314
444
  end
315
445
 
316
- example "mount time works as expected" do
446
+ # This method may be removed
447
+ example 'mount time works as expected' do
317
448
  expect(mount).to respond_to(:mount_time)
318
-
319
- if solaris
320
- expect(mount.mount_time).to be_kind_of(Time)
321
- else
322
- expect(mount.mount_time).to be_nil
323
- end
449
+ expect(mount.mount_time).to be_nil
324
450
  end
325
451
 
326
- example "mount dump_frequency works as expected" do
452
+ example 'mount dump_frequency works as expected' do
327
453
  msg = 'dump_frequency test skipped on this platform'
328
- skip msg if solaris || bsd || darwin
454
+ skip msg if bsd || darwin
329
455
  expect(mount).to respond_to(:dump_frequency)
330
- expect(mount.dump_frequency).to be_kind_of(Numeric)
456
+ expect(mount.dump_frequency).to be_a(Numeric)
331
457
  end
332
458
 
333
- example "mount freq is an alias for dump_frequency" do
459
+ example 'mount freq is an alias for dump_frequency' do
334
460
  expect(mount).to respond_to(:freq)
335
461
  expect(mount.method(:freq)).to eq(mount.method(:dump_frequency))
336
462
  end
337
463
 
338
- example "mount pass_number works as expected" do
464
+ example 'mount pass_number works as expected' do
339
465
  msg = 'pass_number test skipped on this platform'
340
- skip msg if solaris || bsd || darwin
466
+ skip msg if bsd || darwin
341
467
  expect(mount).to respond_to(:pass_number)
342
- expect(mount.pass_number).to be_kind_of(Numeric)
468
+ expect(mount.pass_number).to be_a(Numeric)
343
469
  end
344
470
 
345
- example "mount passno is an alias for pass_number" do
471
+ example 'mount passno is an alias for pass_number' do
346
472
  expect(mount).to respond_to(:passno)
347
473
  expect(mount.method(:passno)).to eq(mount.method(:pass_number))
348
474
  end
349
475
 
350
- example "mount_point singleton method works as expected" do
351
- expect(Sys::Filesystem).to respond_to(:mount_point)
352
- expect{ Sys::Filesystem.mount_point(Dir.pwd) }.not_to raise_error
353
- expect(Sys::Filesystem.mount_point(Dir.pwd)).to be_kind_of(String)
476
+ example 'mount_point singleton method works as expected' do
477
+ expect(described_class).to respond_to(:mount_point)
478
+ expect{ described_class.mount_point(Dir.pwd) }.not_to raise_error
479
+ expect(described_class.mount_point(Dir.pwd)).to be_a(String)
354
480
  end
355
481
 
356
- example "mount singleton method is defined" do
357
- expect(Sys::Filesystem).to respond_to(:mount)
482
+ example 'mount singleton method is defined' do
483
+ expect(described_class).to respond_to(:mount)
358
484
  end
359
485
 
360
- example "umount singleton method is defined" do
361
- expect(Sys::Filesystem).to respond_to(:umount)
486
+ example 'umount singleton method is defined' do
487
+ expect(described_class).to respond_to(:umount)
362
488
  end
363
489
  end
364
490
 
365
- context "FFI" do
491
+ context 'FFI' do
366
492
  before(:context) do
367
493
  require 'mkmf-lite'
368
494
  end
369
495
 
370
496
  let(:dummy) { Class.new { extend Mkmf::Lite } }
371
497
 
372
- example "ffi functions are private" do
373
- expect(Sys::Filesystem.methods.include?('statvfs')).to be false
374
- expect(Sys::Filesystem.methods.include?('strerror')).to be false
498
+ example 'ffi functions are private' do
499
+ expect(described_class.methods.include?('statvfs')).to be false
500
+ expect(described_class.methods.include?('strerror')).to be false
375
501
  end
376
502
 
377
- example "statfs struct is expected size" do
503
+ example 'statfs struct is expected size' do
378
504
  header = bsd || darwin ? 'sys/mount.h' : 'sys/statfs.h'
379
505
  expect(Sys::Filesystem::Structs::Statfs.size).to eq(dummy.check_sizeof('struct statfs', header))
380
506
  end
381
507
 
382
- example "statvfs struct is expected size" do
508
+ example 'statvfs struct is expected size' do
383
509
  expect(Sys::Filesystem::Structs::Statvfs.size).to eq(dummy.check_sizeof('struct statvfs', 'sys/statvfs.h'))
384
510
  end
385
511
 
386
- example "mnttab struct is expected size" do
387
- skip "mnttab test skipped except on Solaris" unless solaris
388
- expect(Sys::Filesystem::Structs::Mnttab.size).to eq(dummy.check_sizeof('struct mnttab', 'sys/mnttab.h'))
512
+ example 'mntent struct is expected size' do
513
+ skip 'mnttab test skipped except on Linux' unless linux
514
+ expect(Sys::Filesystem::Structs::Mntent.size).to eq(dummy.check_sizeof('struct mntent', 'mntent.h'))
389
515
  end
390
516
 
391
- example "mntent struct is expected size" do
392
- skip "mnttab test skipped except on Linux" unless linux
393
- expect(Sys::Filesystem::Structs::Mntent.size).to eq(dummy.check_sizeof('struct mntent', 'mntent.h'))
517
+ example 'a failed statvfs call behaves as expected' do
518
+ msg = 'statvfs() function failed: No such file or directory'
519
+ expect{ described_class.stat('/whatever') }.to raise_error(Sys::Filesystem::Error, msg)
520
+ end
521
+
522
+ example 'statvfs alias is used for statvfs64' do
523
+ expect(Sys::Filesystem::Functions.attached_functions[:statvfs]).to be_a(FFI::Function)
524
+ expect(Sys::Filesystem::Functions.attached_functions[:statvfs64]).to be_nil
525
+ end
526
+ end
527
+
528
+ describe 'linux64? method' do
529
+ let(:functions_class) { Sys::Filesystem::Functions }
530
+
531
+ # Helper method to test linux64? with mocked config
532
+ def test_linux64_with_config(host_os, pointer_size, ruby_platform = nil, java_arch = nil)
533
+ # Mock RbConfig::CONFIG
534
+ allow(RbConfig::CONFIG).to receive(:[]).and_call_original
535
+ allow(RbConfig::CONFIG).to receive(:[]).with('host_os').and_return(host_os)
536
+
537
+ # When running under JRuby, we need to handle it differently
538
+ if RUBY_PLATFORM == 'java'
539
+ # Under JRuby, always mock ENV_JAVA since that's the path the code will take
540
+ if java_arch
541
+ # This is a JRuby-specific test
542
+ allow(ENV_JAVA).to receive(:[]).with('sun.arch.data.model').and_return(java_arch.to_s)
543
+ else
544
+ # This is meant to test regular Ruby logic, but under JRuby we need to mock ENV_JAVA
545
+ # to make it take the "regular Ruby" path by returning nil/empty
546
+ expected_arch = pointer_size == 8 ? '64' : '32'
547
+ allow(ENV_JAVA).to receive(:[]).with('sun.arch.data.model').and_return(expected_arch)
548
+ end
549
+ else
550
+ # Running under regular Ruby
551
+ # Determine arch and DEFS based on host_os for the new multi-check approach
552
+ if pointer_size == 8
553
+ # For 64-bit systems, make arch contain "64"
554
+ arch_value = host_os.include?('64') ? host_os : host_os + '64'
555
+ defs_value = '-DSOMETHING=1'
556
+ else
557
+ # For 32-bit systems, ensure neither arch nor DEFS contain "64"
558
+ arch_value = host_os.gsub(/64/, '32')
559
+ defs_value = '-DSOMETHING=1'
560
+ end
561
+
562
+ allow(RbConfig::CONFIG).to receive(:[]).with('arch').and_return(arch_value)
563
+ allow(RbConfig::CONFIG).to receive(:[]).with('DEFS').and_return(defs_value)
564
+
565
+ if ruby_platform == 'java'
566
+ # Mock RUBY_PLATFORM for JRuby tests
567
+ stub_const('RUBY_PLATFORM', 'java')
568
+
569
+ # Mock ENV_JAVA for JRuby
570
+ env_java_mock = double('ENV_JAVA')
571
+ allow(env_java_mock).to receive(:[]).with('sun.arch.data.model').and_return(java_arch.to_s)
572
+ stub_const('ENV_JAVA', env_java_mock)
573
+ else
574
+ # Mock the pack method for regular Ruby (last resort check)
575
+ packed_data = 'x' * pointer_size
576
+ allow_any_instance_of(Array).to receive(:pack).with('P').and_return(packed_data)
577
+ end
578
+ end
579
+
580
+ functions_class.send(:linux64?)
581
+ end
582
+
583
+ context 'with different Linux distributions on 64-bit architectures' do
584
+ let(:linux_distros) do
585
+ {
586
+ 'x86_64-linux-gnu' => 'Ubuntu/Debian x86_64',
587
+ 'x86_64-pc-linux-gnu' => 'Generic x86_64 Linux',
588
+ 'aarch64-linux-gnu' => 'ARM64 (Raspberry Pi 4, AWS Graviton)',
589
+ 's390x-linux-gnu' => 'IBM Z mainframe',
590
+ 'powerpc64le-linux-gnu' => 'POWER8/9 little-endian',
591
+ 'powerpc64-linux-gnu' => 'POWER8/9 big-endian',
592
+ 'mips64el-linux-gnuabi64' => 'MIPS64 little-endian',
593
+ 'alpha-linux-gnu' => 'DEC Alpha',
594
+ 'sparc64-linux-gnu' => 'SPARC64',
595
+ 'riscv64-linux-gnu' => 'RISC-V 64-bit'
596
+ }
597
+ end
598
+
599
+ it 'returns true for 64-bit Linux systems' do
600
+ linux_distros.each do |host_os, description|
601
+ result = test_linux64_with_config(host_os, 8)
602
+ expect(result).to be_truthy, "Expected linux64? to return true for #{host_os} (#{description})"
603
+ end
604
+ end
605
+ end
606
+
607
+ context 'with different Linux distributions on 32-bit architectures' do
608
+ let(:linux_32bit_distros) do
609
+ {
610
+ 'i386-linux-gnu' => '32-bit x86',
611
+ 'i486-linux-gnu' => '32-bit x86',
612
+ 'i586-linux-gnu' => '32-bit x86',
613
+ 'i686-linux-gnu' => '32-bit x86',
614
+ 'arm-linux-gnueabihf' => 'ARM 32-bit hard-float',
615
+ 'armv7l-linux-gnueabihf' => 'ARMv7 32-bit',
616
+ 'mips-linux-gnu' => 'MIPS 32-bit',
617
+ 'mipsel-linux-gnu' => 'MIPS 32-bit little-endian',
618
+ 'powerpc-linux-gnu' => 'PowerPC 32-bit',
619
+ 's390-linux-gnu' => 'IBM S/390 32-bit'
620
+ }
621
+ end
622
+
623
+ it 'returns false for 32-bit Linux systems' do
624
+ linux_32bit_distros.each do |host_os, description|
625
+ result = test_linux64_with_config(host_os, 4)
626
+ expect(result).to be_falsey, "Expected linux64? to return false for #{host_os} (#{description})"
627
+ end
628
+ end
629
+ end
630
+
631
+ context 'with non-Linux operating systems' do
632
+ let(:non_linux_os) do
633
+ {
634
+ 'darwin21.6.0' => 'macOS',
635
+ 'freebsd13.1' => 'FreeBSD',
636
+ 'openbsd7.2' => 'OpenBSD',
637
+ 'netbsd9.3' => 'NetBSD',
638
+ 'dragonfly6.4' => 'DragonFlyBSD',
639
+ 'solaris2.11' => 'Solaris',
640
+ 'aix7.2.0.0' => 'AIX',
641
+ 'mingw32' => 'Windows MSYS2',
642
+ 'cygwin' => 'Cygwin'
643
+ }
644
+ end
645
+
646
+ it 'returns false for non-Linux systems regardless of architecture' do
647
+ non_linux_os.each do |host_os, description|
648
+ # Test both 32-bit and 64-bit scenarios
649
+ [4, 8].each do |pointer_size|
650
+ result = test_linux64_with_config(host_os, pointer_size)
651
+ expect(result).to be_falsey,
652
+ "Expected linux64? to return false for #{host_os} (#{description}) with #{pointer_size * 8}-bit pointers"
653
+ end
654
+ end
655
+ end
656
+ end
657
+
658
+ context 'with JRuby on different platforms' do
659
+ it 'returns true for 64-bit Linux on JRuby' do
660
+ result = test_linux64_with_config('x86_64-linux-gnu', nil, 'java', 64)
661
+ expect(result).to be_truthy
662
+ end
663
+
664
+ it 'returns false for 32-bit Linux on JRuby' do
665
+ result = test_linux64_with_config('i386-linux-gnu', nil, 'java', 32)
666
+ expect(result).to be_falsey
667
+ end
668
+
669
+ it 'returns false for non-Linux systems on JRuby' do
670
+ result = test_linux64_with_config('darwin21.6.0', nil, 'java', 64)
671
+ expect(result).to be_falsey
672
+ end
673
+ end
674
+
675
+ context 'edge cases' do
676
+ it 'handles case-insensitive Linux detection' do
677
+ ['LINUX-gnu', 'Linux-gnu', 'linux-GNU'].each do |host_os|
678
+ result = test_linux64_with_config(host_os, 8)
679
+ expect(result).to be_truthy, "Expected linux64? to handle case-insensitive matching for #{host_os}"
680
+ end
681
+ end
682
+
683
+ it 'handles partial Linux matches in host_os string' do
684
+ ['some-linux-variant', 'embedded-linux-system', 'custom-linux-build'].each do |host_os|
685
+ result = test_linux64_with_config(host_os, 8)
686
+ expect(result).to be_truthy, "Expected linux64? to match partial Linux strings for #{host_os}"
687
+ end
688
+ end
689
+ end
690
+
691
+ context 'multi-check priority order', unless: RUBY_PLATFORM == 'java' do
692
+ it 'uses arch check first when arch contains 64' do
693
+ allow(RbConfig::CONFIG).to receive(:[]).and_call_original
694
+ allow(RbConfig::CONFIG).to receive(:[]).with('host_os').and_return('x86_64-linux-gnu')
695
+ allow(RbConfig::CONFIG).to receive(:[]).with('arch').and_return('x86_64-linux')
696
+ allow(RbConfig::CONFIG).to receive(:[]).with('DEFS').and_return('')
697
+
698
+ # Should not need to call pack method since arch check succeeds
699
+ expect_any_instance_of(Array).not_to receive(:pack)
700
+
701
+ expect(functions_class.send(:linux64?)).to be_truthy
702
+ end
703
+
704
+ it 'uses DEFS check when arch does not contain 64 but DEFS does' do
705
+ allow(RbConfig::CONFIG).to receive(:[]).and_call_original
706
+ allow(RbConfig::CONFIG).to receive(:[]).with('host_os').and_return('special-linux-gnu')
707
+ allow(RbConfig::CONFIG).to receive(:[]).with('arch').and_return('special-linux')
708
+ allow(RbConfig::CONFIG).to receive(:[]).with('DEFS').and_return('-D__LP64__=1')
709
+
710
+ # Should not need to call pack method since DEFS check succeeds
711
+ expect_any_instance_of(Array).not_to receive(:pack)
712
+
713
+ expect(functions_class.send(:linux64?)).to be_truthy
714
+ end
715
+
716
+ it 'falls back to pack method when neither arch nor DEFS contain 64' do
717
+ allow(RbConfig::CONFIG).to receive(:[]).and_call_original
718
+ allow(RbConfig::CONFIG).to receive(:[]).with('host_os').and_return('custom-linux-gnu')
719
+ allow(RbConfig::CONFIG).to receive(:[]).with('arch').and_return('custom-linux')
720
+ allow(RbConfig::CONFIG).to receive(:[]).with('DEFS').and_return('-DSOMETHING=1')
721
+
722
+ # Should call pack method as last resort
723
+ allow_any_instance_of(Array).to receive(:pack).with('P').and_return('12345678')
724
+
725
+ expect(functions_class.send(:linux64?)).to be_truthy
726
+ end
727
+
728
+ it 'returns false when all checks fail on 32-bit' do
729
+ allow(RbConfig::CONFIG).to receive(:[]).and_call_original
730
+ allow(RbConfig::CONFIG).to receive(:[]).with('host_os').and_return('custom-linux-gnu')
731
+ allow(RbConfig::CONFIG).to receive(:[]).with('arch').and_return('custom-linux')
732
+ allow(RbConfig::CONFIG).to receive(:[]).with('DEFS').and_return('-DSOMETHING=1')
733
+
734
+ # Pack method returns 4 bytes (32-bit)
735
+ allow_any_instance_of(Array).to receive(:pack).with('P').and_return('1234')
736
+
737
+ expect(functions_class.send(:linux64?)).to be_falsey
738
+ end
394
739
  end
395
740
  end
396
741
  end