sys-filesystem 0.2.0-x86-mswin32-60

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.
data/CHANGES ADDED
@@ -0,0 +1,15 @@
1
+ == 0.2.0 - 30-Dec-2008
2
+ * Added the Filesystem.mounts method for iterating over mount or volume
3
+ information.
4
+
5
+ == 0.1.1 - 28-Mar-2007
6
+ * Bug fix for BSD flavors. Thanks go to Jeremy Kemper and Ole Christian
7
+ Rynning for the spot.
8
+ * Bug fix for OS X (along the same lines as the BSD fix). Thanks go to
9
+ Aurelian Dehay for the spot.
10
+ * Some Rdoc improvements for the C extension.
11
+ * Tweaks to the gemspec.
12
+ * Added synopsis to the README.
13
+
14
+ == 0.1.0 - 17-Nov-2006
15
+ * Initial release. Alpha. Code is stable, but API is not.
data/MANIFEST ADDED
@@ -0,0 +1,13 @@
1
+ * MANIFEST
2
+ * CHANGES
3
+ * Rakefile
4
+ * README
5
+ * sys-fileystem.gemspec
6
+ * examples/example_stat.rb
7
+ * doc/sys-filesystem.txt
8
+ * ext/extconf.rb
9
+ * ext/filesystem.c
10
+ * lib/sys/filesystem.rb
11
+ * test/test_sys_filesystem.rb
12
+ * test/test_sys_filesystem_unix
13
+ * test/test_sys_filesystem_windows
data/README ADDED
@@ -0,0 +1,72 @@
1
+ = Description
2
+ A Ruby interface for getting file system information.
3
+
4
+ = Prerequisites
5
+ === MS Windows
6
+ * windows-pr, 0.9.8 or later.
7
+
8
+ = Installation
9
+ rake test (optional)
10
+ rake install (non-gem) OR rake install_gem (gem)
11
+
12
+ = Synopsis
13
+ require 'sys/filesystem'
14
+ include Sys
15
+
16
+ p Filesystem.stat("/")
17
+
18
+ # Sample output
19
+
20
+ #<Sys::Filesystem::Stat:0x517440
21
+ @base_type = "ufs",
22
+ @flags = 4,
23
+ @files_available = 3817457,
24
+ @block_size = 8192,
25
+ @blocks_available = 19957633,
26
+ @blocks = 34349612,
27
+ @name_max = 255,
28
+ @path = "/",
29
+ @filesystem_id = 35651592,
30
+ @files = 4135040,
31
+ @fragment_size = 1024,
32
+ @files_free = 3817457,
33
+ @blocks_free = 20301129
34
+ >
35
+
36
+ Filesystem.mounts{ |mount| p mount }
37
+
38
+ = Notes
39
+ === MS Windows
40
+ This is a pure Ruby implementation using the windows-pr package, which in
41
+ turn wraps native Windows functions.
42
+ === UNIX
43
+ This is a C extension that wraps statvfs, etc.
44
+
45
+ = Sample code
46
+ Run 'rake example' if you want to see a basic sample run. The actual code
47
+ is 'example_stat.rb' in the 'examples' directory. Modify it as you see fit.
48
+
49
+ = Known Bugs
50
+ None that I'm aware of. Please report bugs on the project page at
51
+ http://www.rubyforge.org/projects/sysutils.
52
+
53
+ = Future Plans
54
+ Suggestions welcome.
55
+
56
+ = Acknowledgements
57
+ Mike Hall, for ideas and code that I borrowed from his 'filesystem' package.
58
+ Park Heesob, for implementation and API ideas for the MS Windows version.
59
+
60
+ = Copyright
61
+ (C) 2003-2008 Daniel J. Berger
62
+ All Rights Reserved
63
+
64
+ = Warranty
65
+ This library is provided "as is" and without any express or
66
+ implied warranties, including, without limitation, the implied
67
+ warranties of merchantability and fitness for a particular purpose.
68
+
69
+ = Author
70
+ Daniel J. Berger
71
+ djberg96 at gmail dot com
72
+ imperator on IRC (irc.freenode.net)
data/Rakefile ADDED
@@ -0,0 +1,72 @@
1
+ require 'rake'
2
+ require 'rake/clean'
3
+ require 'rake/testtask'
4
+ include Config
5
+
6
+ desc "Clean the build files for the sys-filesystem source for UNIX systems"
7
+ task :clean do
8
+ Dir.chdir('examples') do
9
+ FileUtils.rm_rf('sys') if File.exists?('sys')
10
+ end
11
+
12
+ unless CONFIG['host_os'].match('mswin')
13
+ file = 'sys/filesystem.' + CONFIG['DLEXT']
14
+ Dir.chdir('ext') do
15
+ sh 'make distclean' rescue nil
16
+ rm file if File.exists?(file)
17
+ end
18
+ end
19
+ end
20
+
21
+ desc "Build the sys-filesystem library on UNIX systems (but don't install it)"
22
+ task :build => [:clean] do
23
+ unless CONFIG['host_os'].match('mswin')
24
+ file = 'filesystem.' + CONFIG['DLEXT']
25
+ Dir.chdir('ext') do
26
+ ruby 'extconf.rb'
27
+ sh 'make'
28
+ mv file, 'sys'
29
+ end
30
+ end
31
+ end
32
+
33
+ if CONFIG['host_os'].match('mswin')
34
+ desc "Install the sys-filesystem library"
35
+ task :install do
36
+ install_dir = File.join(CONFIG['sitelibdir'], 'sys')
37
+ Dir.mkdir(install_dir) unless File.exists?(install_dir)
38
+ FileUtils.cp('lib/sys/filesystem.rb', install_dir, :verbose => true)
39
+ end
40
+ else
41
+ desc "Install the sys-filesystem library"
42
+ task :install => [:build] do
43
+ Dir.chdir('ext') do
44
+ sh 'make install'
45
+ end
46
+ end
47
+ end
48
+
49
+ desc "Run the test suite"
50
+ Rake::TestTask.new("test") do |t|
51
+ unless CONFIG['host_os'].match('mswin')
52
+ task :test => :build
53
+ t.libs << 'ext'
54
+ t.libs.delete('lib')
55
+ end
56
+ t.warning = true
57
+ t.verbose = true
58
+ t.test_files = FileList['test/test_sys_filesystem.rb']
59
+ end
60
+
61
+ desc "Run the example program"
62
+ task :example => [:build] do |t|
63
+ Dir.chdir('examples') do
64
+ Dir.mkdir('sys') unless File.exists?('sys')
65
+ end
66
+
67
+ FileUtils.cp('ext/sys/filesystem.' + Config::CONFIG['DLEXT'], 'examples/sys')
68
+
69
+ Dir.chdir('examples') do
70
+ ruby 'example_stat.rb'
71
+ end
72
+ end
@@ -0,0 +1,165 @@
1
+ = Description
2
+ A Ruby interface for getting filesystem information.
3
+
4
+ = Synopsis
5
+ require 'sys/filesystem'
6
+ include Sys
7
+
8
+ p Filesystem.stat("/") # => Sys::Filesystem::Stat object
9
+
10
+ Filesystem.mounts{ |mount|
11
+ p mount
12
+ }
13
+
14
+ = Constants
15
+ == Sys::Filesystem
16
+ VERSION
17
+ The version of this package, returned as a string.
18
+
19
+ == Sys::Filesystem::Stat
20
+ RDONLY
21
+ Read only filesystem.
22
+
23
+ See the +flags+ method for more information.
24
+
25
+ NOSUID
26
+ Filesystem does not support suid or sgid semantics.
27
+
28
+ See the +flags+ method for more information.
29
+
30
+ NOTRUNC
31
+ Filesystem does not truncate file names longer than +name_max+. Not
32
+ supported on all platforms.
33
+
34
+ See the +flags+ method for more information.
35
+
36
+ = Class Methods
37
+ === Sys::Filesystem
38
+ Sys::Filesystem.stat(path)
39
+ Returns a Filesystem::Stat object containing information about the
40
+ +path+ filesystem.
41
+
42
+ Sys::Filesystem.mounts
43
+ Returns an array of Filesystem::Mount objects containing information
44
+ about the mount points available on your system.
45
+
46
+ In block form this method yields each Mount object in turn instead
47
+ of returning an array.
48
+
49
+ = Instance Methods
50
+ === Sys::Filesystem::Mount
51
+ name
52
+ The name of the mounted resource.
53
+
54
+ On MS Windows this is the device mapping.
55
+
56
+ mount_time
57
+ The last time the volume was mounted.
58
+
59
+ On MS Windows this is your system's boot time.
60
+
61
+ mount_type
62
+ The type of mount, e.g. NFS, NTFS.
63
+
64
+ mount_point
65
+ The volume mount point.
66
+
67
+ On MS Windows this is the volume letter.
68
+
69
+ options
70
+ A list of comma separated options that denote properties of the volume.
71
+
72
+ pass_number
73
+ The number of the filesystem check, or nil if not present.
74
+
75
+ This is always nil on MS Windows.
76
+
77
+ frequency
78
+ The dump frequency in days, or nil if not present or supported.
79
+
80
+ This is always nil on MS Windows.
81
+
82
+ === Sys::Filesystem::Stat
83
+ base_type
84
+ The filesystem type, e.g. UFS.
85
+
86
+ block_size
87
+ The preferred system block size.
88
+
89
+ blocks
90
+ The total number of +fragment_size+ blocks in the filesystem.
91
+
92
+ blocks_available
93
+ The number of free blocks available to unprivileged processes.
94
+
95
+ blocks_free
96
+ The total number of free blocks in the filesystem.
97
+
98
+ files
99
+ The total number of files/inodes that can be created.
100
+
101
+ files_free
102
+ The total number of free files/inodes on the file system.
103
+
104
+ filesystem_id
105
+ The filesystem identifier.
106
+
107
+ flags
108
+ A bit mask of flags. See the 'Constants' section for a list of flags.
109
+
110
+ fragment_size
111
+ The fragment size, i.e. fundamental file system block size.
112
+
113
+ inodes
114
+ Alias for +files+.
115
+
116
+ inodes_free
117
+ Alias for +files_free+.
118
+
119
+ inodes_available
120
+ Alias for +files_available+.
121
+
122
+ name_max
123
+ The maximum length of a file name permitted on the file system.
124
+
125
+ path
126
+ The path of the filesystem.
127
+
128
+ = Fixnum helper methods
129
+ Fixnum#to_gb
130
+ Returns a number in terms of gigabytes.
131
+
132
+ Fixnum#to_kb
133
+ Returns a number in terms of kilobytes
134
+
135
+ Fixnum#to_mb
136
+ Returns a number in terms of megabytes
137
+
138
+ == Known Bugs
139
+ None that I am aware of. Please log any bugs you find on the project
140
+ website at http://www.rubyforge.org/projects/sysutils.
141
+
142
+ == License
143
+ Ruby's
144
+
145
+ == Copyright
146
+ Copyright 2002-2008, Daniel J. Berger
147
+
148
+ All Rights Reserved. This module is free software. It may be used,
149
+ redistributed and/or modified under the same terms as Ruby itself.
150
+
151
+ == Warranty
152
+ This library is provided "as is" and without any express or
153
+ implied warranties, including, without limitation, the implied
154
+ warranties of merchantability and fitness for a particular purpose.
155
+
156
+ == Acknowledgements
157
+ Mike Hall for his original source code.
158
+
159
+ == Author
160
+ Daniel J. Berger
161
+ djberg96 at nospam at gmail dot com
162
+ imperator on IRC (Freenode)
163
+
164
+ == See Also
165
+ mount
@@ -0,0 +1,24 @@
1
+ ######################################################################
2
+ # example_stat.rb
3
+ #
4
+ # Example program that demonstrates the FileSystem.stat method.
5
+ # Use the 'rake example' task to run this program.
6
+ ######################################################################
7
+ require 'sys/filesystem'
8
+ include Sys
9
+
10
+ p Filesystem::VERSION
11
+
12
+ stat = Filesystem.stat("/")
13
+ puts "Path: " + stat.path
14
+ puts "Block size: " + stat.block_size.to_s
15
+ puts "Fragment size: " + stat.fragment_size.to_s
16
+ puts "Blocks free: " + stat.blocks_free.to_s
17
+ puts "Blocks available: " + stat.blocks_available.to_s
18
+ puts "Files/Inodes: " + stat.files.to_s
19
+ puts "Files/Inodes free: " + stat.files_free.to_s
20
+ puts "Files/Inodes available: " + stat.files_available.to_s
21
+ puts "File system id: " + stat.filesystem_id.to_s
22
+ puts "Base type: " + stat.base_type if stat.base_type
23
+ puts "Flags: " + stat.flags.to_s
24
+ puts "Name max: " + stat.name_max.to_s
@@ -0,0 +1,392 @@
1
+ require 'windows/error'
2
+ require 'windows/filesystem'
3
+ require 'windows/volume'
4
+ require 'windows/handle'
5
+ require 'windows/limits'
6
+ require 'socket'
7
+ require 'win32ole'
8
+ require 'date'
9
+ require 'time'
10
+
11
+ # The Sys module serves as a namespace only.
12
+ module Sys
13
+
14
+ # The Filesystem class encapsulates information about your filesystem.
15
+ class Filesystem
16
+ include Windows::Error
17
+ include Windows::Handle
18
+ include Windows::Limits
19
+
20
+ extend Windows::Error
21
+ extend Windows::FileSystem
22
+ extend Windows::Volume
23
+
24
+ # Error typically raised if any of the Sys::Filesystem methods fail.
25
+ class Error < StandardError; end
26
+
27
+ CASE_SENSITIVE_SEARCH = 0x00000001
28
+ CASE_PRESERVED_NAMES = 0x00000002
29
+ UNICODE_ON_DISK = 0x00000004
30
+ PERSISTENT_ACLS = 0x00000008
31
+ FILE_COMPRESSION = 0x00000010
32
+ VOLUME_QUOTAS = 0x00000020
33
+ SUPPORTS_SPARSE_FILES = 0x00000040
34
+ SUPPORTS_REPARSE_POINTS = 0x00000080
35
+ SUPPORTS_REMOTE_STORAGE = 0x00000100
36
+ VOLUME_IS_COMPRESSED = 0x00008000
37
+ SUPPORTS_OBJECT_IDS = 0x00010000
38
+ SUPPORTS_ENCRYPTION = 0x00020000
39
+ NAMED_STREAMS = 0x00040000
40
+ READ_ONLY_VOLUME = 0x00080000
41
+
42
+ VERSION = '0.2.0'
43
+
44
+ class Mount
45
+ # The name of the volume. This is the device mapping.
46
+ attr_reader :name
47
+
48
+ # The last time the volume was mounted. For MS Windows this equates
49
+ # to your system's boot time.
50
+ attr_reader :mount_time
51
+
52
+ # The type of mount, e.g. NTFS, UDF, etc.
53
+ attr_reader :mount_type
54
+
55
+ # The volume mount point, e.g. 'C:\'
56
+ attr_reader :mount_point
57
+
58
+ # Various comma separated options that reflect the volume's features
59
+ attr_reader :options
60
+
61
+ # Always nil on MS Windows. Provided for interface compatibility only.
62
+ attr_reader :pass_number
63
+
64
+ # Always nil on MS Windows. Provided for interface compatibility only.
65
+ attr_reader :frequency
66
+
67
+ alias fsname name
68
+ alias dir mount_point
69
+ alias opts options
70
+ alias passno pass_number
71
+ alias freq frequency
72
+ end
73
+
74
+ class Stat
75
+ # The path of the file system.
76
+ attr_reader :path
77
+
78
+ # The file system block size. MS Windows typically defaults to 4096.
79
+ attr_reader :block_size
80
+
81
+ # Fragment size. Meaningless at the moment.
82
+ attr_reader :fragment_size
83
+
84
+ # The total number of blocks available (used or unused) on the file
85
+ # system.
86
+ attr_reader :blocks
87
+
88
+ # The total number of unused blocks.
89
+ attr_reader :blocks_free
90
+
91
+ # The total number of unused blocks available to unprivileged
92
+ # processes. Identical to +blocks+ at the moment.
93
+ attr_reader :blocks_available
94
+
95
+ # Total number of files/inodes that can be created on the file system.
96
+ # This attribute is always nil on MS Windows.
97
+ attr_reader :files
98
+
99
+ # Total number of free files/inodes that can be created on the file
100
+ # system. This attribute is always nil on MS Windows.
101
+ attr_reader :files_free
102
+
103
+ # Total number of available files/inodes for unprivileged processes
104
+ # that can be created on the file system. This attribute is always
105
+ # nil on MS Windows.
106
+ attr_reader :files_available
107
+
108
+ # The file system volume id.
109
+ attr_reader :filesystem_id
110
+
111
+ # A bit mask of file system flags.
112
+ attr_reader :flags
113
+
114
+ # The maximum length of a file name permitted on the file system.
115
+ attr_reader :name_max
116
+
117
+ # The file system type, e.g. NTFS, FAT, etc.
118
+ attr_reader :base_type
119
+
120
+ alias inodes files
121
+ alias inodes_free files_free
122
+ alias inodes_available files_available
123
+ end
124
+
125
+ # Yields a Filesystem::Mount object for each volume on your system in
126
+ # block form. Returns an array of Filesystem::Mount objects in non-block
127
+ # form.
128
+ #
129
+ # Example:
130
+ #
131
+ # Filesystem.mounts{ |mount|
132
+ # p mt.name # => \\Device\\HarddiskVolume1
133
+ # p mt.mount_point # => C:\
134
+ # p mt.mount_time # => Thu Dec 18 20:12:08 -0700 2008
135
+ # p mt.mount_type # => NTFS
136
+ # p mt.options # => casepres,casesens,ro,unicode
137
+ # p mt.pass_number # => nil
138
+ # p mt.dump_freq # => nil
139
+ # }
140
+ #
141
+ # This method is a bit of a fudge for MS Windows in the name of interface
142
+ # compatibility because this method deals with volumes, not actual mount
143
+ # points. But, I believe it provides the sort of information many users
144
+ # want at a glance.
145
+ #
146
+ # The possible values for the +options+ and their meanings are as follows:
147
+ #
148
+ # casepres => The filesystem preserves the case of file names when it places a name on disk.
149
+ # casesens => The filesystem supports case-sensitive file names.
150
+ # compression => The filesystem supports file-based compression.
151
+ # namedstreams => The filesystem supports named streams.
152
+ # pacls => The filesystem preserves and enforces access control lists.
153
+ # ro => The filesystem is read-only.
154
+ # encryption => The filesystem supports the Encrypted File System (EFS).
155
+ # objids => The filesystem supports object identifiers.
156
+ # rpoints => The filesystem supports reparse points.
157
+ # sparse => The filesystem supports sparse files.
158
+ # unicode => The filesystem supports Unicode in file names as they appear on disk.
159
+ # compressed => The filesystem is compressed.
160
+ #
161
+ def self.mounts
162
+ buffer = 0.chr * MAXPATH
163
+ length = GetLogicalDriveStrings(buffer.size, buffer)
164
+
165
+ if length == 0
166
+ raise Error, get_last_error
167
+ end
168
+
169
+ mounts = block_given? ? nil : []
170
+
171
+ # Try again if it fails
172
+ if length > buffer.size
173
+ buffer = 0.chr * length
174
+ if GetLogicalDriveStrings(buffer.size, buffer) == 0
175
+ raise Error, get_last_error
176
+ end
177
+ end
178
+
179
+ boot_time = get_boot_time
180
+
181
+ drives = buffer.strip.split("\0")
182
+
183
+ drives.each{ |drive|
184
+ mount = Mount.new
185
+ volume = 0.chr * MAXPATH
186
+ fsname = 0.chr * MAXPATH
187
+
188
+ mount.instance_variable_set(:@mount_point, drive)
189
+ mount.instance_variable_set(:@mount_time, boot_time)
190
+
191
+ volume_serial_number = [0].pack('L')
192
+ max_component_length = [0].pack('L')
193
+ filesystem_flags = [0].pack('L')
194
+
195
+ bool = GetVolumeInformation(
196
+ drive,
197
+ volume,
198
+ volume.size,
199
+ volume_serial_number,
200
+ max_component_length,
201
+ filesystem_flags,
202
+ fsname,
203
+ fsname.size
204
+ )
205
+
206
+ # Skip unmounted floppies or cd-roms
207
+ unless bool
208
+ errnum = GetLastError()
209
+ if errnum == ERROR_NOT_READY
210
+ next
211
+ else
212
+ raise Error, get_last_error(errnum)
213
+ end
214
+ end
215
+
216
+ filesystem_flags = filesystem_flags.unpack('L')[0]
217
+
218
+ name = 0.chr * MAXPATH
219
+
220
+ if QueryDosDevice(drive[0,2], name, name.size) == 0
221
+ raise Error, get_last_error
222
+ end
223
+
224
+ mount.instance_variable_set(:@name, name.strip)
225
+ mount.instance_variable_set(:@mount_type, fsname.strip)
226
+ mount.instance_variable_set(:@options, get_options(filesystem_flags))
227
+
228
+ if block_given?
229
+ yield mount
230
+ else
231
+ mounts << mount
232
+ end
233
+ }
234
+
235
+ mounts # Nil if the block form was used.
236
+ end
237
+
238
+ # Returns a Filesystem::Stat object that contains information about the
239
+ # +path+ file system.
240
+ #
241
+ # Example:
242
+ #
243
+ # File.stat("C:\\")
244
+ # File.stat("C:\\Documents and Settings\\some_user")
245
+ #
246
+ def self.stat(path)
247
+ bytes_avail = [0].pack('Q')
248
+ bytes_free = [0].pack('Q')
249
+ total_bytes = [0].pack('Q')
250
+
251
+ unless GetDiskFreeSpaceEx(path, bytes_avail, total_bytes, bytes_free)
252
+ raise Error, get_last_error
253
+ end
254
+
255
+ bytes_avail = bytes_avail.unpack('Q').first
256
+ bytes_free = bytes_free.unpack('Q').first
257
+ total_bytes = total_bytes.unpack('Q').first
258
+
259
+ sectors = [0].pack('Q')
260
+ bytes = [0].pack('Q')
261
+ free = [0].pack('Q')
262
+ total = [0].pack('Q')
263
+
264
+ unless GetDiskFreeSpace(path, sectors, bytes, free, total)
265
+ raise Error, get_last_error
266
+ end
267
+
268
+ sectors = sectors.unpack('Q').first
269
+ bytes = bytes.unpack('Q').first
270
+ free = free.unpack('Q').first
271
+ total = total.unpack('Q').first
272
+
273
+ block_size = sectors * bytes
274
+ blocks_avail = total_bytes / block_size
275
+ blocks_free = bytes_free / block_size
276
+
277
+ vol_name = 0.chr * 260
278
+ base_type = 0.chr * 260
279
+ vol_serial = [0].pack('L')
280
+ name_max = [0].pack('L')
281
+ flags = [0].pack('L')
282
+
283
+ bool = GetVolumeInformation(
284
+ path,
285
+ vol_name,
286
+ vol_name.size,
287
+ vol_serial,
288
+ name_max,
289
+ flags,
290
+ base_type,
291
+ base_type.size
292
+ )
293
+
294
+ unless bool
295
+ raise Error, get_last_error
296
+ end
297
+
298
+ vol_serial = vol_serial.unpack('L').first
299
+ name_max = name_max.unpack('L').first
300
+ flags = flags.unpack('L').first
301
+ base_type = base_type[/^[^\0]*/]
302
+
303
+ stat_obj = Stat.new
304
+ stat_obj.instance_variable_set(:@path, path)
305
+ stat_obj.instance_variable_set(:@block_size, block_size)
306
+ stat_obj.instance_variable_set(:@blocks, blocks_avail)
307
+ stat_obj.instance_variable_set(:@blocks_available, blocks_avail)
308
+ stat_obj.instance_variable_set(:@blocks_free, blocks_free)
309
+ stat_obj.instance_variable_set(:@name_max, name_max)
310
+ stat_obj.instance_variable_set(:@base_type, base_type)
311
+ stat_obj.instance_variable_set(:@flags, flags)
312
+ stat_obj.instance_variable_set(:@filesystem_id, vol_serial)
313
+
314
+ stat_obj.freeze # Read-only object
315
+ end
316
+
317
+ private
318
+
319
+ # Used to get the boot time of the system, which is used for mount_time
320
+ # attribute within the File.mounts method.
321
+ #
322
+ def self.get_boot_time
323
+ host = Socket.gethostname
324
+ cs = "winmgmts://#{host}/root/cimv2"
325
+ begin
326
+ wmi = WIN32OLE.connect(cs)
327
+ rescue WIN32OLERuntimeError => e
328
+ raise Error, e
329
+ else
330
+ query = 'select LastBootupTime from Win32_OperatingSystem'
331
+ results = wmi.ExecQuery(query)
332
+ results.each{ |ole|
333
+ time_array = Time.parse(ole.LastBootupTime.split('.').first)
334
+ return Time.mktime(*time_array)
335
+ }
336
+ end
337
+ end
338
+
339
+ # Private method that converts filesystem flags into a comma separated
340
+ # list of strings. The presentation is meant as a rough analogue to the
341
+ # way options are presented for Unix filesystems.
342
+ #
343
+ def self.get_options(flags)
344
+ str = ""
345
+ str << " casepres" if CASE_PRESERVED_NAMES & flags > 0
346
+ str << " casesens" if CASE_SENSITIVE_SEARCH & flags > 0
347
+ str << " compression" if FILE_COMPRESSION & flags > 0
348
+ str << " namedstreams" if NAMED_STREAMS & flags > 0
349
+ str << " pacls" if PERSISTENT_ACLS & flags > 0
350
+ str << " ro" if READ_ONLY_VOLUME & flags > 0
351
+ str << " encryption" if SUPPORTS_ENCRYPTION & flags > 0
352
+ str << " objids" if SUPPORTS_OBJECT_IDS & flags > 0
353
+ str << " rpoints" if SUPPORTS_REPARSE_POINTS & flags > 0
354
+ str << " sparse" if SUPPORTS_SPARSE_FILES & flags > 0
355
+ str << " unicode" if UNICODE_ON_DISK & flags > 0
356
+ str << " compressed" if VOLUME_IS_COMPRESSED & flags > 0
357
+
358
+ str.tr!(' ', ',')
359
+ str = str[1..-1] # Ignore the first comma
360
+ str
361
+ end
362
+
363
+ end
364
+ end
365
+
366
+ # Some convenient methods for converting bytes to kb, mb, and gb.
367
+ #
368
+ class Fixnum
369
+ # call-seq:
370
+ # <tt>fix</tt>.to_kb
371
+ #
372
+ # Returns +fix+ in terms of kilobytes.
373
+ def to_kb
374
+ self / 1024
375
+ end
376
+
377
+ # call-seq:
378
+ # <tt>fix</tt>.to_mb
379
+ #
380
+ # Returns +fix+ in terms of megabytes.
381
+ def to_mb
382
+ self / 1048576
383
+ end
384
+
385
+ # call-seq:
386
+ # <tt>fix</tt>.to_gb
387
+ #
388
+ # Returns +fix+ in terms of gigabytes.
389
+ def to_gb
390
+ self / 1073741824
391
+ end
392
+ end
@@ -0,0 +1,36 @@
1
+ require 'rubygems'
2
+
3
+ spec = Gem::Specification.new do |gem|
4
+ gem.name = 'sys-filesystem'
5
+ gem.version = '0.2.0'
6
+ gem.author = 'Daniel J. Berger'
7
+ gem.email = 'djberg96@gmail.com'
8
+ gem.homepage = 'http://www.rubyforge.org/projects/sysutils'
9
+ gem.platform = Gem::Platform::RUBY
10
+ gem.summary = 'A Ruby interface for getting file system information.'
11
+ gem.description = 'A Ruby interface for getting file system information.'
12
+ gem.test_file = 'test/test_sys_filesystem.rb'
13
+ gem.has_rdoc = true
14
+ gem.extra_rdoc_files = ['CHANGES', 'README', 'MANIFEST']
15
+ gem.rubyforge_project = 'sysutils'
16
+ files = Dir["doc/*"] + Dir["examples/*"] + Dir["test/*"] + Dir["[A-Z]*"]
17
+ files.delete_if{ |item| item.include?('CVS') }
18
+ gem.files = files
19
+ end
20
+
21
+ if $PROGRAM_NAME == __FILE__
22
+ if RUBY_PLATFORM.match('mswin')
23
+ spec.required_ruby_version = '>= 1.8.2'
24
+ spec.files += ['lib/sys/filesystem.rb']
25
+ spec.platform = Gem::Platform::CURRENT
26
+ spec.add_dependency('windows-pr', '>= 0.6.0')
27
+ else
28
+ spec.required_ruby_version = '>= 1.8.0'
29
+ spec.extensions = ['ext/extconf.rb']
30
+ spec.files += Dir["ext/**/*"]
31
+ spec.extra_rdoc_files << 'ext/sys/filesystem.c'
32
+ end
33
+
34
+ Gem.manage_gems if Gem::RubyGemsVersion.to_f < 1.0
35
+ Gem::Builder.new(spec).build
36
+ end
@@ -0,0 +1,9 @@
1
+ $LOAD_PATH.unshift File.dirname(File.expand_path(__FILE__))
2
+
3
+ require 'rbconfig'
4
+
5
+ if Config::CONFIG['host_os'].match('mswin')
6
+ require 'test_sys_filesystem_windows'
7
+ else
8
+ require 'test_sys_filesystem_unix'
9
+ end
@@ -0,0 +1,234 @@
1
+ ####################################################################
2
+ # tc_unix.rb
3
+ #
4
+ # Test case for the Sys::Filesystem.stat method and related stuff.
5
+ # This test suite should be run via the 'rake test' task.
6
+ ####################################################################
7
+ require 'rubygems'
8
+ gem 'test-unit'
9
+
10
+ require 'test/unit'
11
+ require 'sys/filesystem'
12
+ include Sys
13
+
14
+ class TC_Sys_Filesystem_Unix < Test::Unit::TestCase
15
+ def self.startup
16
+ @@solaris = Config::CONFIG['host_os'] =~ /solaris/i
17
+ @@linux = Config::CONFIG['host_os'] =~ /linux/i
18
+ end
19
+
20
+ def setup
21
+ @dir = "/"
22
+ @stat = Filesystem.stat(@dir)
23
+ @mnt = Filesystem.mounts[0]
24
+ @size = 58720256
25
+ @array = []
26
+ end
27
+
28
+ def test_version
29
+ assert_equal('0.2.0', Filesystem::VERSION)
30
+ end
31
+
32
+ def test_stat_path
33
+ assert_respond_to(@stat, :path)
34
+ assert_equal("/", @stat.path)
35
+ end
36
+
37
+ def test_stat_block_size
38
+ assert_respond_to(@stat, :block_size)
39
+ assert_kind_of(Fixnum, @stat.block_size)
40
+ end
41
+
42
+ def test_stat_fragment_size
43
+ assert_respond_to(@stat, :fragment_size)
44
+ assert_kind_of(Fixnum, @stat.fragment_size)
45
+ end
46
+
47
+ def test_stat_blocks
48
+ assert_respond_to(@stat, :blocks)
49
+ assert_kind_of(Fixnum, @stat.blocks)
50
+ end
51
+
52
+ def test_stat_blocks_free
53
+ assert_respond_to(@stat, :blocks_free)
54
+ assert_kind_of(Fixnum, @stat.blocks_free)
55
+ end
56
+
57
+ def test_stat_blocks_available
58
+ assert_respond_to(@stat, :blocks_available)
59
+ assert_kind_of(Fixnum, @stat.blocks_available)
60
+ end
61
+
62
+ def test_stat_files
63
+ assert_respond_to(@stat, :files)
64
+ assert_kind_of(Fixnum, @stat.files)
65
+ end
66
+
67
+ def test_inodes_alias
68
+ assert_respond_to(@stat, :inodes)
69
+ assert_true(@stat.method(:inodes) == @stat.method(:files))
70
+ end
71
+
72
+ def test_stat_files_free
73
+ assert_respond_to(@stat, :files_free)
74
+ assert_kind_of(Fixnum, @stat.files_free)
75
+ end
76
+
77
+ def test_stat_inodes_free_alias
78
+ assert_respond_to(@stat, :inodes_free)
79
+ assert_true(@stat.method(:inodes_free) == @stat.method(:files_free))
80
+ end
81
+
82
+ def test_stat_files_available
83
+ assert_respond_to(@stat, :files_available)
84
+ assert_kind_of(Fixnum, @stat.files_available)
85
+ end
86
+
87
+ def test_stat_inodes_available_alias
88
+ assert_respond_to(@stat, :inodes_available)
89
+ assert_true(@stat.method(:inodes_available) == @stat.method(:files_available))
90
+ end
91
+
92
+ def test_stat_filesystem_id
93
+ assert_respond_to(@stat, :filesystem_id)
94
+ assert_kind_of(Integer, @stat.filesystem_id)
95
+ end
96
+
97
+ def test_stat_flags
98
+ assert_respond_to(@stat, :flags)
99
+ assert_kind_of(Fixnum, @stat.flags)
100
+ end
101
+
102
+ def test_stat_name_max
103
+ assert_respond_to(@stat, :name_max)
104
+ assert_kind_of(Fixnum, @stat.name_max)
105
+ end
106
+
107
+ def test_stat_base_type
108
+ omit_unless(@@solaris, "NOTRUNC test skipped except on Solaris")
109
+ assert_respond_to(@stat, :base_type)
110
+ assert_kind_of(String, @stat.base_type)
111
+ end
112
+
113
+ def test_stat_constants
114
+ assert_not_nil(Filesystem::Stat::RDONLY)
115
+ assert_not_nil(Filesystem::Stat::NOSUID)
116
+ omit_unless(@@solaris, "NOTRUNC test skipped except on Solaris")
117
+ assert_not_nil(Filesystem::Stat::NOTRUNC)
118
+ end
119
+
120
+ def test_stat_expected_errors
121
+ assert_raises(ArgumentError){ Filesystem.stat }
122
+ end
123
+
124
+ def test_fixnum_methods_basic
125
+ assert_respond_to(@size, :to_kb)
126
+ assert_respond_to(@size, :to_mb)
127
+ assert_respond_to(@size, :to_gb)
128
+ end
129
+
130
+ def test_to_kb
131
+ assert_equal(57344, @size.to_kb)
132
+ end
133
+
134
+ def test_to_mb
135
+ assert_equal(56, @size.to_mb)
136
+ end
137
+
138
+ def test_to_gb
139
+ assert_equal(0, @size.to_gb)
140
+ end
141
+
142
+ # Filesystem::Mount tests
143
+
144
+ def test_mounts_with_no_block
145
+ assert_nothing_raised{ @array = Filesystem.mounts }
146
+ assert_kind_of(Filesystem::Mount, @array[0])
147
+ end
148
+
149
+ def test_mounts_with_block
150
+ assert_nothing_raised{ Filesystem.mounts{ |m| @array << m } }
151
+ assert_kind_of(Filesystem::Mount, @array[0])
152
+ end
153
+
154
+ def test_mounts_high_iteration
155
+ assert_nothing_raised{ 1000.times{ @array = Filesystem.mounts } }
156
+ end
157
+
158
+ def test_mount_name
159
+ assert_respond_to(@mnt, :name)
160
+ assert_kind_of(String, @mnt.name)
161
+ end
162
+
163
+ def test_fsname_alias
164
+ assert_respond_to(@mnt, :fsname)
165
+ assert_true(@mnt.method(:fsname) == @mnt.method(:name))
166
+ end
167
+
168
+ def test_mount_point
169
+ assert_respond_to(@mnt, :mount_point)
170
+ assert_kind_of(String, @mnt.mount_point)
171
+ end
172
+
173
+ def test_dir_alias
174
+ assert_respond_to(@mnt, :dir)
175
+ assert_true(@mnt.method(:dir) == @mnt.method(:mount_point))
176
+ end
177
+
178
+ def test_mount_type
179
+ assert_respond_to(@mnt, :mount_type)
180
+ assert_kind_of(String, @mnt.mount_type)
181
+ end
182
+
183
+ def test_mount_options
184
+ assert_respond_to(@mnt, :options)
185
+ assert_kind_of(String, @mnt.options)
186
+ end
187
+
188
+ def test_opts_alias
189
+ assert_respond_to(@mnt, :opts)
190
+ assert_true(@mnt.method(:opts) == @mnt.method(:options))
191
+ end
192
+
193
+ def test_mount_time
194
+ assert_respond_to(@mnt, :mount_time)
195
+ if @@solaris
196
+ assert_kind_of(String, @mnt.mount_time)
197
+ else
198
+ assert_nil(@mnt.mount_time)
199
+ end
200
+ end
201
+
202
+ def test_mount_dump_frequency
203
+ omit_if(@@solaris, 'dump_frequency test skipped on Solaris')
204
+ assert_respond_to(@mnt, :dump_frequency)
205
+ assert_kind_of(Fixnum, @mnt.dump_frequency)
206
+ end
207
+
208
+ def test_freq_alias
209
+ assert_respond_to(@mnt, :freq)
210
+ assert_true(@mnt.method(:freq) == @mnt.method(:dump_frequency))
211
+ end
212
+
213
+ def test_mount_pass_number
214
+ omit_if(@@solaris, 'pass_number test skipped on Solaris')
215
+ assert_respond_to(@mnt, :pass_number)
216
+ assert_kind_of(Fixnum, @mnt.pass_number)
217
+ end
218
+
219
+ def test_passno_alias
220
+ assert_respond_to(@mnt, :passno)
221
+ assert_true(@mnt.method(:passno) == @mnt.method(:pass_number))
222
+ end
223
+
224
+ def teardown
225
+ @dir = nil
226
+ @stat = nil
227
+ @array = nil
228
+ end
229
+
230
+ def self.shutdown
231
+ @@solaris = nil
232
+ @@linux = nil
233
+ end
234
+ end
@@ -0,0 +1,192 @@
1
+ ####################################################################
2
+ # tc_windows.rb
3
+ #
4
+ # Test case for the Sys::Filesystem.stat method and related stuff.
5
+ # This should be run via the 'rake test' task.
6
+ ####################################################################
7
+ require 'rubygems'
8
+ gem 'test-unit'
9
+
10
+ require 'test/unit'
11
+ require 'sys/filesystem'
12
+ require 'rbconfig'
13
+ include Sys
14
+
15
+ class TC_Sys_Filesystem_Windows < Test::Unit::TestCase
16
+ def setup
17
+ @dir = '/'
18
+ @stat = Filesystem.stat(@dir)
19
+ @mount = Filesystem.mounts[0]
20
+ @size = 58720256
21
+ @array = []
22
+ end
23
+
24
+ def test_version
25
+ assert_equal('0.2.0', Filesystem::VERSION)
26
+ end
27
+
28
+ def test_stat_path
29
+ assert_respond_to(@stat, :path)
30
+ assert_equal("/", @stat.path)
31
+ end
32
+
33
+ def test_stat_block_size
34
+ assert_respond_to(@stat, :block_size)
35
+ assert_kind_of(Fixnum, @stat.block_size)
36
+ end
37
+
38
+ def test_stat_fragment_size
39
+ assert_respond_to(@stat, :fragment_size)
40
+ assert_nil(@stat.fragment_size)
41
+ end
42
+
43
+ def test_stat_blocks
44
+ assert_respond_to(@stat, :blocks)
45
+ assert_kind_of(Fixnum, @stat.blocks)
46
+ end
47
+
48
+ def test_stat_blocks_free
49
+ assert_respond_to(@stat, :blocks_free)
50
+ assert_kind_of(Fixnum, @stat.blocks_free)
51
+ end
52
+
53
+ def test_stat_blocks_available
54
+ assert_respond_to(@stat, :blocks_available)
55
+ assert_kind_of(Fixnum, @stat.blocks_available)
56
+ end
57
+
58
+ def test_stat_files
59
+ assert_respond_to(@stat, :files)
60
+ assert_respond_to(@stat, :inodes) # Alias
61
+ assert_nil(@stat.files)
62
+ end
63
+
64
+ def test_stat_files_free
65
+ assert_respond_to(@stat, :files_free)
66
+ assert_respond_to(@stat, :inodes_free) # Alias
67
+ assert_nil(@stat.files_free)
68
+ end
69
+
70
+ def test_stat_files_available
71
+ assert_respond_to(@stat, :files_available)
72
+ assert_respond_to(@stat, :inodes_available) # Alias
73
+ assert_nil(@stat.files_available)
74
+ end
75
+
76
+ def test_stat_filesystem_id
77
+ assert_respond_to(@stat, :filesystem_id)
78
+ assert_kind_of(Integer, @stat.filesystem_id)
79
+ end
80
+
81
+ def test_stat_flags
82
+ assert_respond_to(@stat, :flags)
83
+ assert_kind_of(Fixnum, @stat.flags)
84
+ end
85
+
86
+ def test_stat_name_max
87
+ assert_respond_to(@stat, :name_max)
88
+ assert_kind_of(Fixnum, @stat.name_max)
89
+ end
90
+
91
+ def test_stat_base_type
92
+ assert_respond_to(@stat, :base_type)
93
+ assert_kind_of(String, @stat.base_type)
94
+ end
95
+
96
+ def test_constants
97
+ assert_not_nil(Filesystem::CASE_SENSITIVE_SEARCH)
98
+ assert_not_nil(Filesystem::CASE_PRESERVED_NAMES)
99
+ assert_not_nil(Filesystem::UNICODE_ON_DISK)
100
+ assert_not_nil(Filesystem::PERSISTENT_ACLS)
101
+ assert_not_nil(Filesystem::FILE_COMPRESSION)
102
+ assert_not_nil(Filesystem::VOLUME_QUOTAS)
103
+ assert_not_nil(Filesystem::SUPPORTS_SPARSE_FILES)
104
+ assert_not_nil(Filesystem::SUPPORTS_REPARSE_POINTS)
105
+ assert_not_nil(Filesystem::SUPPORTS_REMOTE_STORAGE)
106
+ assert_not_nil(Filesystem::VOLUME_IS_COMPRESSED)
107
+ assert_not_nil(Filesystem::SUPPORTS_OBJECT_IDS)
108
+ assert_not_nil(Filesystem::SUPPORTS_ENCRYPTION)
109
+ assert_not_nil(Filesystem::NAMED_STREAMS)
110
+ assert_not_nil(Filesystem::READ_ONLY_VOLUME)
111
+ end
112
+
113
+ def test_stat_expected_errors
114
+ assert_raises(ArgumentError){ Filesystem.stat }
115
+ end
116
+
117
+ # Filesystem.mounts
118
+
119
+ def test_mounts_constructor_basic
120
+ assert_respond_to(Filesystem, :mounts)
121
+ assert_nothing_raised{ Filesystem.mounts }
122
+ assert_nothing_raised{ Filesystem.mounts{} }
123
+ end
124
+
125
+ def test_mounts
126
+ assert_kind_of(Array, Filesystem.mounts)
127
+ assert_kind_of(Filesystem::Mount, Filesystem.mounts[0])
128
+ end
129
+
130
+ def test_mounts_block_form
131
+ assert_nil(Filesystem.mounts{})
132
+ assert_nothing_raised{ Filesystem.mounts{ |mt| @array << mt }}
133
+ assert_kind_of(Filesystem::Mount, @array[0])
134
+ end
135
+
136
+ def test_mount_name
137
+ assert_respond_to(@mount, :name)
138
+ assert_kind_of(String, @mount.name)
139
+ end
140
+
141
+ def test_mount_time
142
+ assert_respond_to(@mount, :mount_time)
143
+ assert_kind_of(Time, @mount.mount_time)
144
+ end
145
+
146
+ def test_mount_type
147
+ assert_respond_to(@mount, :mount_type)
148
+ assert_kind_of(String, @mount.mount_type)
149
+ end
150
+
151
+ def test_mount_point
152
+ assert_respond_to(@mount, :mount_point)
153
+ assert_kind_of(String, @mount.mount_point)
154
+ end
155
+
156
+ def test_mount_options
157
+ assert_respond_to(@mount, :options)
158
+ assert_kind_of(String, @mount.options)
159
+ end
160
+
161
+ def test_pass_number
162
+ assert_respond_to(@mount, :pass_number)
163
+ assert_nil(@mount.pass_number)
164
+ end
165
+
166
+ def test_frequency
167
+ assert_respond_to(@mount, :frequency)
168
+ assert_nil(@mount.frequency)
169
+ end
170
+
171
+ def test_mounts_expected_errors
172
+ assert_raise(ArgumentError){ Filesystem.mounts("C:\\") }
173
+ end
174
+
175
+ def test_fixnum_methods
176
+ assert_respond_to(@size, :to_kb)
177
+ assert_respond_to(@size, :to_mb)
178
+ assert_respond_to(@size, :to_gb)
179
+
180
+ assert_equal(57344, @size.to_kb)
181
+ assert_equal(56, @size.to_mb)
182
+ assert_equal(0, @size.to_gb)
183
+ end
184
+
185
+ def teardown
186
+ @array = nil
187
+ @dir = nil
188
+ @stat = nil
189
+ @size = nil
190
+ @mount = nil
191
+ end
192
+ end
metadata ADDED
@@ -0,0 +1,79 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: sys-filesystem
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.2.0
5
+ platform: x86-mswin32-60
6
+ authors:
7
+ - Daniel J. Berger
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+
12
+ date: 2008-12-30 00:00:00 -07:00
13
+ default_executable:
14
+ dependencies:
15
+ - !ruby/object:Gem::Dependency
16
+ name: windows-pr
17
+ type: :runtime
18
+ version_requirement:
19
+ version_requirements: !ruby/object:Gem::Requirement
20
+ requirements:
21
+ - - ">="
22
+ - !ruby/object:Gem::Version
23
+ version: 0.6.0
24
+ version:
25
+ description: A Ruby interface for getting file system information.
26
+ email: djberg96@gmail.com
27
+ executables: []
28
+
29
+ extensions: []
30
+
31
+ extra_rdoc_files:
32
+ - CHANGES
33
+ - README
34
+ - MANIFEST
35
+ files:
36
+ - doc/sys-filesystem.txt
37
+ - examples/example_stat.rb
38
+ - test/test_sys_filesystem.rb
39
+ - test/test_sys_filesystem_unix.rb
40
+ - test/test_sys_filesystem_windows.rb
41
+ - CHANGES
42
+ - doc
43
+ - examples
44
+ - ext
45
+ - lib
46
+ - MANIFEST
47
+ - Rakefile
48
+ - README
49
+ - sys-filesystem.gemspec
50
+ - test
51
+ - lib/sys/filesystem.rb
52
+ has_rdoc: true
53
+ homepage: http://www.rubyforge.org/projects/sysutils
54
+ post_install_message:
55
+ rdoc_options: []
56
+
57
+ require_paths:
58
+ - lib
59
+ required_ruby_version: !ruby/object:Gem::Requirement
60
+ requirements:
61
+ - - ">="
62
+ - !ruby/object:Gem::Version
63
+ version: 1.8.2
64
+ version:
65
+ required_rubygems_version: !ruby/object:Gem::Requirement
66
+ requirements:
67
+ - - ">="
68
+ - !ruby/object:Gem::Version
69
+ version: "0"
70
+ version:
71
+ requirements: []
72
+
73
+ rubyforge_project: sysutils
74
+ rubygems_version: 1.3.1
75
+ signing_key:
76
+ specification_version: 2
77
+ summary: A Ruby interface for getting file system information.
78
+ test_files:
79
+ - test/test_sys_filesystem.rb