sys-filesystem-1.1.7/0000755000175000017500000000000012754302416013550 5ustar pravipravisys-filesystem-1.1.7/examples/0000755000175000017500000000000012754302416015366 5ustar pravipravisys-filesystem-1.1.7/examples/example_stat.rb0000644000175000017500000000161612754302416020405 0ustar pravipravi###################################################################### # example_stat.rb # # Example program that demonstrates the FileSystem.stat method. # Use the 'rake example' task to run this program. ###################################################################### require 'sys/filesystem' include Sys p Filesystem::VERSION stat = Filesystem.stat("/") puts "Path: " + stat.path puts "Block size: " + stat.block_size.to_s puts "Fragment size: " + stat.fragment_size.to_s puts "Blocks free: " + stat.blocks_free.to_s puts "Blocks available: " + stat.blocks_available.to_s puts "Files/Inodes: " + stat.files.to_s puts "Files/Inodes free: " + stat.files_free.to_s puts "Files/Inodes available: " + stat.files_available.to_s puts "File system id: " + stat.filesystem_id.to_s puts "Base type: " + stat.base_type if stat.base_type puts "Flags: " + stat.flags.to_s puts "Name max: " + stat.name_max.to_s sys-filesystem-1.1.7/certs/0000755000175000017500000000000012754302416014670 5ustar pravipravisys-filesystem-1.1.7/certs/djberg96_pub.pem0000600000175000017500000000234512754302416017651 0ustar pravipravi-----BEGIN CERTIFICATE----- MIIDcDCCAligAwIBAgIBATANBgkqhkiG9w0BAQUFADA/MREwDwYDVQQDDAhkamJl cmc5NjEVMBMGCgmSJomT8ixkARkWBWdtYWlsMRMwEQYKCZImiZPyLGQBGRYDY29t MB4XDTE1MDkwMjIwNDkxOFoXDTE2MDkwMTIwNDkxOFowPzERMA8GA1UEAwwIZGpi ZXJnOTYxFTATBgoJkiaJk/IsZAEZFgVnbWFpbDETMBEGCgmSJomT8ixkARkWA2Nv bTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAMyTkvXqRp6hLs9eoJOS Hmi8kRYbq9Vkf15/hMxJpotYMgJVHHWrmDcC5Dye2PbnXjTkKf266Zw0PtT9h+lI S3ts9HO+vaCFSMwFFZmnWJSpQ3CNw2RcHxjWkk9yF7imEM8Kz9ojhiDXzBetdV6M gr0lV/alUr7TNVBDngbXEfTWscyXh1qd7xZ4EcOdsDktCe5G45N/o3662tPQvJsi FOF0CM/KuBsa/HL1/eoEmF4B3EKIRfTHrQ3hu20Kv3RJ88QM4ec2+0dd97uX693O zv6981fyEg+aXLkxrkViM/tz2qR2ZE0jPhHTREPYeMEgptRkTmWSKAuLVWrJEfgl DtkCAwEAAaN3MHUwCQYDVR0TBAIwADALBgNVHQ8EBAMCBLAwHQYDVR0OBBYEFEwe nn6bfJADmuIDiMSOzedOrL+xMB0GA1UdEQQWMBSBEmRqYmVyZzk2QGdtYWlsLmNv bTAdBgNVHRIEFjAUgRJkamJlcmc5NkBnbWFpbC5jb20wDQYJKoZIhvcNAQEFBQAD ggEBAHmNOCWoDVD75zHFueY0viwGDVP1BNGFC+yXcb7u2GlK+nEMCORqzURbYPf7 tL+/hzmePIRz7i30UM//64GI1NLv9jl7nIwjhPpXpf7/lu2I9hOTsvwSumb5UiKC /sqBxI3sfj9pr79Wpv4MuikX1XPik7Ncb7NPsJPw06Lvyc3Hkg5X2XpPtLtS+Gr2 wKJnmzb5rIPS1cmsqv0M9LPWflzfwoZ/SpnmhagP+g05p8bRNKjZSA2iImM/GyYZ EJYzxdPOrx2n6NYR3Hk+vHP0U7UBSveI6+qx+ndQYaeyCn+GRX2PKS9h66YF/Q1V tGSHgAmcLlkdGgan182qsE/4kKM= -----END CERTIFICATE----- sys-filesystem-1.1.7/data.tar.gz.sig0000444000175000017500000000040012754302416016361 0ustar pravipravijF 4.B { 0b;HioKz2.tܴ+{]t NtHg7רp-9P))1 f(gF?5ދL<_}>/%qd')϶YkQrfVh㞆Q)3J'p9Ut!wЈBA_9OA= H;)n2ykTC;l?ab,LI>ʩ]2>IjU;fTX@eZ3sys-filesystem-1.1.7/checksums.yaml.gz.sig0000444000175000017500000000040012754302416017611 0ustar pravipravig^Y<&mQݖC,0*^vM*9Y}1 /'yW%rnۦkGX򴛀-\z {mݧpeOrѪXD3({+T') )dyS}肯8fXO 9X;o0x;8]Of|Ǧ~:<]ICz~"WPBoS?[Nc*]]TFUsys-filesystem-1.1.7/lib/0000755000175000017500000000000012754302416014316 5ustar pravipravisys-filesystem-1.1.7/lib/sys-filesystem.rb0000644000175000017500000000004212754302416017637 0ustar pravipravirequire_relative 'sys/filesystem' sys-filesystem-1.1.7/lib/sys/0000755000175000017500000000000012754302416015134 5ustar pravipravisys-filesystem-1.1.7/lib/sys/filesystem.rb0000644000175000017500000000035312754302416017646 0ustar pravipravimodule Sys class Filesystem # The version of the sys-filesystem library VERSION = '1.1.7'.freeze end end if File::ALT_SEPARATOR require_relative 'windows/sys/filesystem' else require_relative 'unix/sys/filesystem' end sys-filesystem-1.1.7/lib/sys/windows/0000755000175000017500000000000012754302416016626 5ustar pravipravisys-filesystem-1.1.7/lib/sys/windows/sys/0000755000175000017500000000000012754302416017444 5ustar pravipravisys-filesystem-1.1.7/lib/sys/windows/sys/filesystem.rb0000644000175000017500000003275412754302416022170 0ustar pravipravirequire_relative 'filesystem/constants' require_relative 'filesystem/functions' require_relative 'filesystem/helper' require 'socket' require 'win32ole' require 'date' require 'time' # The Sys module serves as a namespace only. module Sys # The Filesystem class encapsulates information about your filesystem. class Filesystem include Sys::Filesystem::Constants extend Sys::Filesystem::Functions # Error typically raised if any of the Sys::Filesystem methods fail. class Error < StandardError; end class Mount # The name of the volume. This is the device mapping. attr_reader :name # The last time the volume was mounted. For MS Windows this equates # to your system's boot time. attr_reader :mount_time # The type of mount, e.g. NTFS, UDF, etc. attr_reader :mount_type # The volume mount point, e.g. 'C:\' attr_reader :mount_point # Various comma separated options that reflect the volume's features attr_reader :options # Always nil on MS Windows. Provided for interface compatibility only. attr_reader :pass_number # Always nil on MS Windows. Provided for interface compatibility only. attr_reader :frequency alias fsname name alias dir mount_point alias opts options alias passno pass_number alias freq frequency end class Stat # The path of the file system. attr_reader :path # The file system block size. MS Windows typically defaults to 4096. attr_reader :block_size # Fragment size. Meaningless at the moment. attr_reader :fragment_size # The total number of blocks available (used or unused) on the file # system. attr_reader :blocks # The total number of unused blocks. attr_reader :blocks_free # The total number of unused blocks available to unprivileged processes. attr_reader :blocks_available # Total number of files/inodes that can be created on the file system. # This attribute is always nil on MS Windows. attr_reader :files # Total number of free files/inodes that can be created on the file # system. This attribute is always nil on MS Windows. attr_reader :files_free # Total number of available files/inodes for unprivileged processes # that can be created on the file system. This attribute is always # nil on MS Windows. attr_reader :files_available # The file system volume id. attr_reader :filesystem_id # A bit mask of file system flags. attr_reader :flags # The maximum length of a file name permitted on the file system. attr_reader :name_max # The file system type, e.g. NTFS, FAT, etc. attr_reader :base_type # Returns the total amount of free space on the partition. attr_reader :bytes_free alias inodes files alias inodes_free files_free alias inodes_available files_available # Returns the total space on the partition. def bytes_total blocks * block_size end # Returns the total amount of used space on the partition. def bytes_used bytes_total - bytes_free end # Returns the percentage of the partition that has been used. def percent_used 100 - (100.0 * bytes_free.to_f / bytes_total.to_f) end end # Yields a Filesystem::Mount object for each volume on your system in # block form. Returns an array of Filesystem::Mount objects in non-block # form. # # Example: # # Sys::Filesystem.mounts{ |mount| # p mt.name # => \\Device\\HarddiskVolume1 # p mt.mount_point # => C:\ # p mt.mount_time # => Thu Dec 18 20:12:08 -0700 2008 # p mt.mount_type # => NTFS # p mt.options # => casepres,casesens,ro,unicode # p mt.pass_number # => nil # p mt.dump_freq # => nil # } # # This method is a bit of a fudge for MS Windows in the name of interface # compatibility because this method deals with volumes, not actual mount # points. But, I believe it provides the sort of information many users # want at a glance. # # The possible values for the +options+ and their meanings are as follows: # # casepres => The filesystem preserves the case of file names when it places a name on disk. # casesens => The filesystem supports case-sensitive file names. # compression => The filesystem supports file-based compression. # namedstreams => The filesystem supports named streams. # pacls => The filesystem preserves and enforces access control lists. # ro => The filesystem is read-only. # encryption => The filesystem supports the Encrypted File System (EFS). # objids => The filesystem supports object identifiers. # rpoints => The filesystem supports reparse points. # sparse => The filesystem supports sparse files. # unicode => The filesystem supports Unicode in file names as they appear on disk. # compressed => The filesystem is compressed. # #-- # I couldn't really find a good reason to use the wide functions for this # method. If you have one, patches welcome. # def self.mounts # First call, get needed buffer size buffer = 0.chr length = GetLogicalDriveStringsA(buffer.size, buffer) if length == 0 raise SystemCallError.new('GetLogicalDriveStrings', FFI.errno) else buffer = 0.chr * length end mounts = block_given? ? nil : [] # Try again with new buffer size if GetLogicalDriveStringsA(buffer.size, buffer) == 0 raise SystemCallError.new('GetLogicalDriveStrings', FFI.errno) end drives = buffer.split(0.chr) boot_time = get_boot_time drives.each{ |drive| mount = Mount.new volume = FFI::MemoryPointer.new(:char, MAXPATH) fsname = FFI::MemoryPointer.new(:char, MAXPATH) mount.instance_variable_set(:@mount_point, drive) mount.instance_variable_set(:@mount_time, boot_time) volume_serial_number = FFI::MemoryPointer.new(:ulong) max_component_length = FFI::MemoryPointer.new(:ulong) filesystem_flags = FFI::MemoryPointer.new(:ulong) bool = GetVolumeInformationA( drive, volume, volume.size, volume_serial_number, max_component_length, filesystem_flags, fsname, fsname.size ) # Skip unmounted floppies or cd-roms, or inaccessible drives unless bool if [5,21].include?(FFI.errno) # ERROR_NOT_READY or ERROR_ACCESS_DENIED next else raise SystemCallError.new('GetVolumeInformation', FFI.errno) end end filesystem_flags = filesystem_flags.read_ulong fsname = fsname.read_string name = 0.chr * MAXPATH if QueryDosDeviceA(drive[0,2], name, name.size) == 0 raise SystemCallError.new('QueryDosDevice', FFI.errno) end mount.instance_variable_set(:@name, name.strip) mount.instance_variable_set(:@mount_type, fsname) mount.instance_variable_set(:@options, get_options(filesystem_flags)) if block_given? yield mount else mounts << mount end } mounts # Nil if the block form was used. end # Returns the mount point for the given +file+. For MS Windows this # means the root of the path. # # Example: # # File.mount_point("C:\\Documents and Settings") # => "C:\\' # def self.mount_point(file) wfile = FFI::MemoryPointer.from_string(file.wincode) if PathStripToRootW(wfile) wfile.read_string(wfile.size).split("\000\000").first.tr(0.chr, '') else nil end end # Returns a Filesystem::Stat object that contains information about the # +path+ file system. On Windows this will default to using the root # path for volume information. # # Examples: # # Sys::Filesystem.stat("C:\\") # Sys::Filesystem.stat("C:\\Documents and Settings\\some_user") # def self.stat(path) bytes_avail = FFI::MemoryPointer.new(:ulong_long) bytes_free = FFI::MemoryPointer.new(:ulong_long) total_bytes = FFI::MemoryPointer.new(:ulong_long) mpoint = mount_point(path) wpath = path.wincode # We need this call for the 64 bit support unless GetDiskFreeSpaceExW(wpath, bytes_avail, total_bytes, bytes_free) raise SystemCallError.new('GetDiskFreeSpaceEx', FFI.errno) end bytes_avail = bytes_avail.read_ulong_long bytes_free = bytes_free.read_ulong_long total_bytes = total_bytes.read_ulong_long sectors_ptr = FFI::MemoryPointer.new(:ulong_long) bytes_ptr = FFI::MemoryPointer.new(:ulong_long) free_ptr = FFI::MemoryPointer.new(:ulong_long) total_ptr = FFI::MemoryPointer.new(:ulong_long) # We need this call for the total/cluster info, which is not in the Ex call. unless GetDiskFreeSpaceW(wpath, sectors_ptr, bytes_ptr, free_ptr, total_ptr) raise SystemCallError.new('GetDiskFreeSpace', FFI.errno) end sectors_per_cluster = sectors_ptr.read_ulong_long bytes_per_sector = bytes_ptr.read_ulong_long free_ptr.free total_ptr.free block_size = sectors_per_cluster * bytes_per_sector blocks_avail = bytes_avail / block_size blocks_free = bytes_free / block_size total_blocks = total_bytes / block_size vol_name_ptr = FFI::MemoryPointer.new(:char, MAXPATH) base_type_ptr = FFI::MemoryPointer.new(:char, MAXPATH) vol_serial_ptr = FFI::MemoryPointer.new(:ulong) name_max_ptr = FFI::MemoryPointer.new(:ulong) flags_ptr = FFI::MemoryPointer.new(:ulong) bool = GetVolumeInformationW( mpoint.wincode, vol_name_ptr, vol_name_ptr.size, vol_serial_ptr, name_max_ptr, flags_ptr, base_type_ptr, base_type_ptr.size ) unless bool raise SystemCallError.new('GetVolumInformation', FFI.errno) end vol_serial = vol_serial_ptr.read_ulong name_max = name_max_ptr.read_ulong flags = flags_ptr.read_ulong base_type = base_type_ptr.read_string(base_type_ptr.size).tr(0.chr, '') # Lets explicitly free our pointers vol_name_ptr.free vol_serial_ptr.free name_max_ptr.free flags_ptr.free base_type_ptr.free sectors_ptr.free bytes_ptr.free stat_obj = Stat.new stat_obj.instance_variable_set(:@path, path) stat_obj.instance_variable_set(:@block_size, block_size) stat_obj.instance_variable_set(:@blocks, total_blocks) stat_obj.instance_variable_set(:@blocks_available, blocks_avail) stat_obj.instance_variable_set(:@blocks_free, blocks_free) stat_obj.instance_variable_set(:@name_max, name_max) stat_obj.instance_variable_set(:@base_type, base_type) stat_obj.instance_variable_set(:@flags, flags) stat_obj.instance_variable_set(:@filesystem_id, vol_serial) stat_obj.instance_variable_set(:@bytes_free, bytes_free) stat_obj.freeze # Read-only object end private # This method is used to get the boot time of the system, which is used # for the mount_time attribute within the File.mounts method. # def self.get_boot_time host = Socket.gethostname cs = "winmgmts://#{host}/root/cimv2" begin wmi = WIN32OLE.connect(cs) rescue WIN32OLERuntimeError => e raise Error, e else query = 'select LastBootupTime from Win32_OperatingSystem' results = wmi.ExecQuery(query) results.each{ |ole| time_array = Time.parse(ole.LastBootupTime.split('.').first) return Time.mktime(*time_array) } end end # Private method that converts filesystem flags into a comma separated # list of strings. The presentation is meant as a rough analogue to the # way options are presented for Unix filesystems. # def self.get_options(flags) str = "" str << " casepres" if CASE_PRESERVED_NAMES & flags > 0 str << " casesens" if CASE_SENSITIVE_SEARCH & flags > 0 str << " compression" if FILE_COMPRESSION & flags > 0 str << " namedstreams" if NAMED_STREAMS & flags > 0 str << " pacls" if PERSISTENT_ACLS & flags > 0 str << " ro" if READ_ONLY_VOLUME & flags > 0 str << " encryption" if SUPPORTS_ENCRYPTION & flags > 0 str << " objids" if SUPPORTS_OBJECT_IDS & flags > 0 str << " rpoints" if SUPPORTS_REPARSE_POINTS & flags > 0 str << " sparse" if SUPPORTS_SPARSE_FILES & flags > 0 str << " unicode" if UNICODE_ON_DISK & flags > 0 str << " compressed" if VOLUME_IS_COMPRESSED & flags > 0 str.tr!(' ', ',') str = str[1..-1] # Ignore the first comma str end end end # Some convenient methods for converting bytes to kb, mb, and gb. # class Numeric # call-seq: # num.to_kb # # Returns +num+ in terms of kilobytes. def to_kb self / 1024 end # call-seq: # num.to_mb # # Returns +num+ in terms of megabytes. def to_mb self / 1048576 end # call-seq: # num.to_gb # # Returns +num+ in terms of gigabytes. def to_gb self / 1073741824 end # call-seq: # num.to_gb # # Returns +num+ in terms of terabytes. def to_tb self / 1099511627776 end end sys-filesystem-1.1.7/lib/sys/windows/sys/filesystem/0000755000175000017500000000000012754302416021630 5ustar pravipravisys-filesystem-1.1.7/lib/sys/windows/sys/filesystem/helper.rb0000644000175000017500000000034012754302416023431 0ustar pravipraviclass String # Convenience method for converting strings to UTF-16LE for wide character # functions that require it. def wincode (self.tr(File::SEPARATOR, File::ALT_SEPARATOR) + 0.chr).encode('UTF-16LE') end end sys-filesystem-1.1.7/lib/sys/windows/sys/filesystem/constants.rb0000644000175000017500000000133612754302416024174 0ustar pravipravimodule Sys class Filesystem module Constants MAXPATH = 260 CASE_SENSITIVE_SEARCH = 0x00000001 CASE_PRESERVED_NAMES = 0x00000002 UNICODE_ON_DISK = 0x00000004 PERSISTENT_ACLS = 0x00000008 FILE_COMPRESSION = 0x00000010 VOLUME_QUOTAS = 0x00000020 SUPPORTS_SPARSE_FILES = 0x00000040 SUPPORTS_REPARSE_POINTS = 0x00000080 SUPPORTS_REMOTE_STORAGE = 0x00000100 VOLUME_IS_COMPRESSED = 0x00008000 SUPPORTS_OBJECT_IDS = 0x00010000 SUPPORTS_ENCRYPTION = 0x00020000 NAMED_STREAMS = 0x00040000 READ_ONLY_VOLUME = 0x00080000 end end end sys-filesystem-1.1.7/lib/sys/windows/sys/filesystem/functions.rb0000644000175000017500000000200112754302416024156 0ustar pravipravirequire 'ffi' module Sys class Filesystem module Functions extend FFI::Library ffi_lib :kernel32 # Make FFI functions private module FFI::Library def attach_pfunc(*args) attach_function(*args) private args[0] end end attach_pfunc :GetDiskFreeSpaceW, [:buffer_in, :pointer, :pointer, :pointer, :pointer], :bool attach_pfunc :GetDiskFreeSpaceExW, [:buffer_in, :pointer, :pointer, :pointer], :bool attach_pfunc :GetLogicalDriveStringsA, [:ulong, :pointer], :ulong attach_pfunc :GetVolumeInformationA, [:buffer_in, :pointer, :ulong, :pointer, :pointer, :pointer, :pointer, :ulong], :bool attach_pfunc :GetVolumeInformationW, [:buffer_in, :pointer, :ulong, :pointer, :pointer, :pointer, :pointer, :ulong], :bool attach_pfunc :QueryDosDeviceA, [:buffer_in, :buffer_out, :ulong], :ulong ffi_lib :shlwapi attach_pfunc :PathStripToRootW, [:pointer], :bool end end end sys-filesystem-1.1.7/lib/sys/unix/0000755000175000017500000000000012754302416016117 5ustar pravipravisys-filesystem-1.1.7/lib/sys/unix/sys/0000755000175000017500000000000012754302416016735 5ustar pravipravisys-filesystem-1.1.7/lib/sys/unix/sys/filesystem.rb0000644000175000017500000002532312754302416021453 0ustar pravipravirequire_relative 'filesystem/constants' require_relative 'filesystem/structs' require_relative 'filesystem/functions' # The Sys module serves as a namespace only. module Sys # The Filesystem class serves as an abstract base class. Its methods # return objects of other types. Do not instantiate. class Filesystem include Sys::Filesystem::Constants include Sys::Filesystem::Structs extend Sys::Filesystem::Functions private # Readable versions of constant names @@opt_names = { MNT_RDONLY => 'read-only', MNT_SYNCHRONOUS => 'synchronous', MNT_NOEXEC => 'noexec', MNT_NOSUID => 'nosuid', MNT_NODEV => 'nodev', MNT_UNION => 'union', MNT_ASYNC => 'asynchronous', MNT_CPROTECT => 'content-protection', MNT_EXPORTED => 'exported', MNT_QUARANTINE => 'quarantined', MNT_LOCAL => 'local', MNT_QUOTA => 'quotas', MNT_ROOTFS => 'rootfs', MNT_DONTBROWSE => 'nobrowse', MNT_IGNORE_OWNERSHIP => 'noowners', MNT_AUTOMOUNTED => 'automounted', MNT_JOURNALED => 'journaled', MNT_NOUSERXATTR => 'nouserxattr', MNT_DEFWRITE => 'defwrite', MNT_NOATIME => 'noatime' } # File used to read mount informtion from. if File.exist?('/etc/mtab') MOUNT_FILE = '/etc/mtab' elsif File.exist?('/etc/mnttab') MOUNT_FILE = '/etc/mnttab' else MOUNT_FILE = 'getmntinfo' end public # The error raised if any of the Filesystem methods fail. class Error < StandardError; end # Stat objects are returned by the Sys::Filesystem.stat method. class Stat # Read-only filesystem RDONLY = 1 # Filesystem does not support suid or sgid semantics. NOSUID = 2 # Filesystem does not truncate file names longer than +name_max+. NOTRUNC = 3 # The path of the filesystem. attr_accessor :path # The preferred system block size. attr_accessor :block_size # The fragment size, i.e. fundamental filesystem block size. attr_accessor :fragment_size # The total number of +fragment_size+ blocks in the filesystem. attr_accessor :blocks # The total number of free blocks in the filesystem. attr_accessor :blocks_free # The number of free blocks available to unprivileged processes. attr_accessor :blocks_available # The total number of files/inodes that can be created. attr_accessor :files # The total number of files/inodes on the filesystem. attr_accessor :files_free # The number of free files/inodes available to unprivileged processes. attr_accessor :files_available # The filesystem identifier. attr_accessor :filesystem_id # A bit mask of flags. attr_accessor :flags # The maximum length of a file name permitted on the filesystem. attr_accessor :name_max # The filesystem type, e.g. UFS. attr_accessor :base_type alias inodes files alias inodes_free files_free alias inodes_available files_available # Creates a new Sys::Filesystem::Stat object. This is meant for # internal use only. Do not instantiate directly. # def initialize @path = nil @block_size = nil @fragment_size = nil @blocks = nil @blocks_free = nil @blocks_available = nil @files = nil @files_free = nil @files_available = nil @filesystem_id = nil @flags = nil @name_max = nil @base_type = nil end # Returns the total space on the partition. def bytes_total blocks * block_size end # Returns the total amount of free space on the partition. def bytes_free blocks_available * block_size end # Returns the total amount of used space on the partition. def bytes_used bytes_total - bytes_free end # Returns the percentage of the partition that has been used. def percent_used 100 - (100.0 * bytes_free.to_f / bytes_total.to_f) end end # Mount objects are returned by the Sys::Filesystem.mounts method. class Mount # The name of the mounted resource. attr_accessor :name # The mount point/directory. attr_accessor :mount_point # The type of filesystem mount, e.g. ufs, nfs, etc. attr_accessor :mount_type # A list of comma separated options for the mount, e.g. nosuid, etc. attr_accessor :options # The time the filesystem was mounted. May be nil. attr_accessor :mount_time # The dump frequency in days. May be nil. attr_accessor :dump_frequency # The pass number of the filessytem check. May be nil. attr_accessor :pass_number alias fsname name alias dir mount_point alias opts options alias passno pass_number alias freq dump_frequency # Creates a Sys::Filesystem::Mount object. This is meant for internal # use only. Do no instantiate directly. # def initialize @name = nil @mount_point = nil @mount_type = nil @options = nil @mount_time = nil @dump_frequency = nil @pass_number = nil end end # Returns a Sys::Filesystem::Stat object containing information about the # +path+ on the filesystem. # def self.stat(path) fs = Statvfs.new if statvfs(path, fs) < 0 raise Error, 'statvfs() function failed: ' + strerror(FFI.errno) end obj = Sys::Filesystem::Stat.new obj.path = path obj.block_size = fs[:f_bsize] obj.fragment_size = fs[:f_frsize] obj.blocks = fs[:f_blocks] obj.blocks_free = fs[:f_bfree] obj.blocks_available = fs[:f_bavail] obj.files = fs[:f_files] obj.files_free = fs[:f_ffree] obj.files_available = fs[:f_favail] obj.filesystem_id = fs[:f_fsid] obj.flags = fs[:f_flag] obj.name_max = fs[:f_namemax] # OSX does things a little differently if RbConfig::CONFIG['host_os'] =~ /darwin|osx|mach/i obj.block_size /= 256 end # FreeBSD 10 does things a little differently too if RbConfig::CONFIG['host_os'] =~ /freebsd10/i obj.block_size = obj.fragment_size end if fs.members.include?(:f_basetype) obj.base_type = fs[:f_basetype].to_s end obj.freeze end # In block form, yields a Sys::Filesystem::Mount object for each mounted # filesytem on the host. Otherwise it returns an array of Mount objects. # # Example: # # Sys::Filesystem.mounts{ |fs| # p fs.name # => '/dev/dsk/c0t0d0s0' # p fs.mount_time # => Thu Dec 11 15:07:23 -0700 2008 # p fs.mount_type # => 'ufs' # p fs.mount_point # => '/' # p fs.options # => local, noowner, nosuid # } # def self.mounts array = block_given? ? nil : [] if respond_to?(:getmntinfo, true) buf = FFI::MemoryPointer.new(:pointer) num = getmntinfo(buf, 2) if num == 0 raise Error, 'getmntinfo() function failed: ' + strerror(FFI.errno) end ptr = buf.get_pointer(0) num.times{ |i| mnt = Statfs.new(ptr) obj = Sys::Filesystem::Mount.new obj.name = mnt[:f_mntfromname].to_s obj.mount_point = mnt[:f_mntonname].to_s obj.mount_type = mnt[:f_fstypename].to_s string = "" flags = mnt[:f_flags] & MNT_VISFLAGMASK @@opt_names.each{ |key,val| if flags & key > 0 if string.empty? string << val else string << ", #{val}" end end flags &= ~key } obj.options = string if block_given? yield obj.freeze else array << obj.freeze end ptr += Statfs.size } else begin if respond_to?(:setmntent, true) method_name = 'setmntent' fp = setmntent(MOUNT_FILE, 'r') else method_name = 'fopen' fp = fopen(MOUNT_FILE, 'r') end if fp.null? raise SystemCallError.new(method_name, FFI.errno) end if RbConfig::CONFIG['host_os'] =~ /sunos|solaris/i mt = Mnttab.new while getmntent(fp, mt) == 0 obj = Sys::Filesystem::Mount.new obj.name = mt[:mnt_special].to_s obj.mount_point = mt[:mnt_mountp].to_s obj.mount_type = mt[:mnt_fstype].to_s obj.options = mt[:mnt_mntopts].to_s obj.mount_time = Time.at(Integer(mt[:mnt_time])) if block_given? yield obj.freeze else array << obj.freeze end end else while ptr = getmntent(fp) break if ptr.null? mt = Mntent.new(ptr) obj = Sys::Filesystem::Mount.new obj.name = mt[:mnt_fsname] obj.mount_point = mt[:mnt_dir] obj.mount_type = mt[:mnt_type] obj.options = mt[:mnt_opts] obj.mount_time = nil obj.dump_frequency = mt[:mnt_freq] obj.pass_number = mt[:mnt_passno] if block_given? yield obj.freeze else array << obj.freeze end end end ensure if fp && !fp.null? if respond_to?(:endmntent, true) endmntent(fp) else fclose(fp) end end end end array end # Returns the mount point of the given +file+, or itself if it cannot # be found. # # Example: # # Sys::Filesystem.mount_point('/home/some_user') # => /home # def self.mount_point(file) dev = File.stat(file).dev val = file self.mounts.each{ |mnt| mp = mnt.mount_point begin if File.stat(mp).dev == dev val = mp break end rescue Errno::EACCES next end } val end end end class Numeric # Converts a number to kilobytes. def to_kb self / 1024 end # Converts a number to megabytes. def to_mb self / 1048576 end # Converts a number to gigabytes. def to_gb self / 1073741824 end # Converts a number to terabytes. def to_tb self / 1099511627776 end end sys-filesystem-1.1.7/lib/sys/unix/sys/filesystem/0000755000175000017500000000000012754302416021121 5ustar pravipravisys-filesystem-1.1.7/lib/sys/unix/sys/filesystem/constants.rb0000644000175000017500000000377112754302416023472 0ustar pravipravimodule Sys class Filesystem module Constants private MNT_RDONLY = 0x00000001 # read only filesystem MNT_SYNCHRONOUS = 0x00000002 # file system written synchronously MNT_NOEXEC = 0x00000004 # can't exec from filesystem MNT_NOSUID = 0x00000008 # don't honor setuid bits on fs MNT_NODEV = 0x00000010 # don't interpret special files MNT_UNION = 0x00000020 # union with underlying filesystem MNT_ASYNC = 0x00000040 # file system written asynchronously MNT_CPROTECT = 0x00000080 # file system supports content protection MNT_EXPORTED = 0x00000100 # file system is exported MNT_QUARANTINE = 0x00000400 # file system is quarantined MNT_LOCAL = 0x00001000 # filesystem is stored locally MNT_QUOTA = 0x00002000 # quotas are enabled on filesystem MNT_ROOTFS = 0x00004000 # identifies the root filesystem MNT_DOVOLFS = 0x00008000 # FS supports volfs (deprecated) MNT_DONTBROWSE = 0x00100000 # FS is not appropriate path to user data MNT_IGNORE_OWNERSHIP = 0x00200000 # VFS will ignore ownership info on FS objects MNT_AUTOMOUNTED = 0x00400000 # filesystem was mounted by automounter MNT_JOURNALED = 0x00800000 # filesystem is journaled MNT_NOUSERXATTR = 0x01000000 # Don't allow user extended attributes MNT_DEFWRITE = 0x02000000 # filesystem should defer writes MNT_MULTILABEL = 0x04000000 # MAC support for individual labels MNT_NOATIME = 0x10000000 # disable update of file access time MNT_VISFLAGMASK = ( MNT_RDONLY | MNT_SYNCHRONOUS | MNT_NOEXEC | MNT_NOSUID | MNT_NODEV | MNT_UNION | MNT_ASYNC | MNT_EXPORTED | MNT_QUARANTINE | MNT_LOCAL | MNT_QUOTA | MNT_ROOTFS | MNT_DOVOLFS | MNT_DONTBROWSE | MNT_IGNORE_OWNERSHIP | MNT_AUTOMOUNTED | MNT_JOURNALED | MNT_NOUSERXATTR | MNT_DEFWRITE | MNT_MULTILABEL | MNT_NOATIME | MNT_CPROTECT ) end end end sys-filesystem-1.1.7/lib/sys/unix/sys/filesystem/functions.rb0000644000175000017500000000251312754302416023457 0ustar pravipravirequire 'ffi' module Sys class Filesystem module Functions extend FFI::Library ffi_lib FFI::Library::LIBC if RbConfig::CONFIG['host_os'] =~ /sunos|solaris/i attach_function(:statvfs, :statvfs64, [:string, :pointer], :int) else attach_function(:statvfs, [:string, :pointer], :int) end attach_function(:strerror, [:int], :string) private_class_method :statvfs, :strerror begin if RbConfig::CONFIG['host_os'] =~ /sunos|solaris/i attach_function(:fopen, [:string, :string], :pointer) attach_function(:fclose, [:pointer], :int) attach_function(:getmntent, [:pointer, :pointer], :int) private_class_method :fopen, :fclose, :getmntent else attach_function(:getmntent, [:pointer], :pointer) attach_function(:setmntent, [:string, :string], :pointer) attach_function(:endmntent, [:pointer], :int) private_class_method :getmntent, :setmntent, :endmntent end rescue FFI::NotFoundError if RbConfig::CONFIG['host_os'] =~ /darwin|osx|mach/i attach_function(:getmntinfo, :getmntinfo64, [:pointer, :int], :int) else attach_function(:getmntinfo, [:pointer, :int], :int) end private_class_method :getmntinfo end end end end sys-filesystem-1.1.7/lib/sys/unix/sys/filesystem/structs.rb0000644000175000017500000001014212754302416023153 0ustar pravipravirequire 'ffi' require 'rbconfig' module Sys class Filesystem module Structs class Statfs < FFI::Struct if RbConfig::CONFIG['host_os'] =~ /bsd/i layout( :f_version, :uint32, :f_type, :uint32, :f_flags, :uint64, :f_bsize, :uint64, :f_iosize, :int64, :f_blocks, :uint64, :f_bfree, :uint64, :f_bavail, :int64, :f_files, :uint64, :f_ffree, :uint64, :f_syncwrites, :uint64, :f_asyncwrites, :uint64, :f_syncreads, :uint64, :f_asyncreads, :uint64, :f_spare, [:uint64, 10], :f_namemax, :uint32, :f_owner, :int32, :f_fsid, [:int32, 2], :f_charspare, [:char, 80], :f_fstypename, [:char, 16], :f_mntfromname, [:char, 88], :f_mntonname, [:char, 88] ) else layout( :f_bsize, :uint32, :f_iosize, :int32, :f_blocks, :uint64, :f_bfree, :uint64, :f_bavail, :uint64, :f_files, :uint64, :f_ffree, :uint64, :f_fsid, [:int32, 2], :f_owner, :int32, :f_type, :uint32, :f_flags, :uint32, :f_fssubtype, :uint32, :f_fstypename, [:char, 16], :f_mntonname, [:char, 1024], :f_mntfromname, [:char, 1024], :f_reserved, [:uint32, 8] ) end end # The Statvfs struct represents struct statvfs from sys/statvfs.h. class Statvfs < FFI::Struct if RbConfig::CONFIG['host_os'] =~ /darwin|osx|mach/i layout( :f_bsize, :ulong, :f_frsize, :ulong, :f_blocks, :uint, :f_bfree, :uint, :f_bavail, :uint, :f_files, :uint, :f_ffree, :uint, :f_favail, :uint, :f_fsid, :ulong, :f_flag, :ulong, :f_namemax, :ulong ) elsif RbConfig::CONFIG['host'] =~ /bsd/i layout( :f_bavail, :uint64, :f_bfree, :uint64, :f_blocks, :uint64, :f_favail, :uint64, :f_ffree, :uint64, :f_files, :uint64, :f_bsize, :ulong, :f_flag, :ulong, :f_frsize, :ulong, :f_fsid, :ulong, :f_namemax, :ulong ) elsif RbConfig::CONFIG['host'] =~ /sunos|solaris/i layout( :f_bsize, :ulong, :f_frsize, :ulong, :f_blocks, :uint64_t, :f_bfree, :uint64_t, :f_bavail, :uint64_t, :f_files, :uint64_t, :f_ffree, :uint64_t, :f_favail, :uint64_t, :f_fsid, :ulong, :f_basetype, [:char, 16], :f_flag, :ulong, :f_namemax, :ulong, :f_fstr, [:char, 32], :f_filler, [:ulong, 16] ) else layout( :f_bsize, :ulong, :f_frsize, :ulong, :f_blocks, :ulong, :f_bfree, :ulong, :f_bavail, :ulong, :f_files, :ulong, :f_ffree, :ulong, :f_favail, :ulong, :f_fsid, :ulong, :f_flag, :ulong, :f_namemax, :ulong, :f_ftype, :ulong, :f_basetype, [:char, 16], :f_str, [:char, 16] ) end end # The Mnttab struct represents struct mnnttab from sys/mnttab.h on Solaris. class Mnttab < FFI::Struct layout( :mnt_special, :string, :mnt_mountp, :string, :mnt_fstype, :string, :mnt_mntopts, :string, :mnt_time, :string ) end # The Mntent struct represents struct mntent from sys/mount.h on Unix. class Mntent < FFI::Struct layout( :mnt_fsname, :string, :mnt_dir, :string, :mnt_type, :string, :mnt_opts, :string, :mnt_freq, :int, :mnt_passno, :int ) end end end end sys-filesystem-1.1.7/metadata.gz.sig0000444000175000017500000000040012754302416016443 0ustar pravipravi q{&d[;=N2աSJlK,_63 MCm{zkx:n/{t[ATC{RD:؎eN$j*7CnkvDo) Xl\c@ P2߻}Jcv{*%7f*PP6?yZPfRƠHL'0Z]'y~Ja"זE6Y[lE,˱0,sys-filesystem-1.1.7/CHANGES0000644000175000017500000000677712754302416014564 0ustar pravipravi== 1.1.7 - 1-Aug-2016 * Fixed an issue in the stat method for MS Windows where the blocks_avail value was not correct. Thanks go to Maxime Lapointe for the spot. == 1.1.6 - 17-May-2016 * On versions that use setmntent or fopen, explicitly raise an error if either of those calls return a null value. == 1.1.5 - 5-Dec-2015 * This gem is now signed. * The gem related tasks in the Rakefile now assume Rubygems 2.x. * Updates to the gemspec, added cert_chain, removed rubyforge_project. * Internal reorganization, and use of relative_require as appropriate. * Added a sys-filesystem.rb file for convenience. == 1.1.4 - 15-Mar-2015 * The File.mounts method no longer raises an error if a mount point is not accessible. Thanks go to Michael Pope for the patch. * Some internal code reorganization. == 1.1.3 - 1-Oct-2014 * Now ignores EPERM errors when trying to find the mount point for a path. Thanks go to petersen for the patch. * The Filesystem.stat method now defaults to using the root path on Windows for volume information. == 1.1.2 - 9-May-2014 * Added the percent_used, bytes_total, bytes_free and bytes_used methods to the Filesystem::Stat class. Thanks go to xanview for the suggestion. * Changed File.exists? to File.exist? to avoid warnings in Ruby 2.1.x. * The convenience methods to_mb, to_gb, etc, are now defined in Numeric instead of Fixnum. * Added the to_tb method for terabytes. * Minor updates to the gem:create and gem:install Rake tasks. == 1.1.1 - 3-Oct-2013 * Solaris now always uses statvfs64 on Solaris for better 64-bit support. Thanks go to Jeff Shantz for the spot. == 1.1.0 - 19-Jan-2013 * Converted the Windows source code to use FFI. Consequently, there is now a single gem rather than separate gems for Windows and Unix. * Revamped the Windows tests. == 1.0.0 - 11-Jan-2012 * Converted everything from C to FFI for the Unix flavors. The Windows source code remains untouched. == 0.3.4 - 19-Nov-2010 * Fixed a bug where negative block counts were happening on very large hard drives. Thanks go to Jonas Pfenniger for the spot. * Refactored the clean task in the Rakefile. * Some cosmetic source code changes. == 0.3.3 - 21-May-2010 * Added a workaround for the Sys::Filesystem#block_size member to deal with a bug in OS X. Thanks go to Josh Pasqualetto for the spot. == 0.3.2 - 29-Dec-2009 * Source has been moved to github. * Added the 'gem' task and removed build logic from the gemspec. * Updated the install task. * Minor correction to the manifest. * Removed some junk build files that were inadvertently included in the last gem. == 0.3.1 - 5-Aug-2009 * Now compatible with Ruby 1.9.x. * Changed license to Artistic 2.0 * Updated the gemspec, including the explicit addition of a license and test-unit as a development dependency, as well as an updated description. == 0.3.0 - 26-Feb-2009 * Added support for OS X and FreeBSD thanks to an awesome patch by Nobuyoshi Miyokawa. * Added the Filesystem.mount_point method that takes a file and returns the mount point it's sitting on. == 0.2.0 - 30-Dec-2008 * Added the Filesystem.mounts method for iterating over mount or volume information. == 0.1.1 - 28-Mar-2007 * Bug fix for BSD flavors. Thanks go to Jeremy Kemper and Ole Christian Rynning for the spot. * Bug fix for OS X (along the same lines as the BSD fix). Thanks go to Aurelian Dehay for the spot. * Some Rdoc improvements for the C extension. * Tweaks to the gemspec. * Added synopsis to the README. == 0.1.0 - 17-Nov-2006 * Initial release. Alpha. Code is stable, but API is not. sys-filesystem-1.1.7/README0000644000175000017500000000410012754302416014423 0ustar pravipravi= Description A Ruby interface for getting file system information. = Installation gem install sys-filesystem = Synopsis require 'sys/filesystem' include Sys # Display information about a particular filesystem. p Filesystem.stat('/') # Sample output # # Describe all mount points on the system Filesystem.mounts{ |mount| p mount } # Find the mount point of any particular file puts Filesystem.mount_point('/home/djberge/some_file.txt') => '/home' = Notes This is a pure Ruby implementation that uses FFI. This means it should work with JRuby, too. = Sample code Run 'rake example' if you want to see a basic sample run. The actual code is 'example_stat.rb' in the 'examples' directory. Modify it as you see fit. = Known Bugs None that I'm aware of. Please report bugs on the project page at https://github.com/djberg96/sys-filesystem = Future Plans Add better 64-bit support for Linux and BSD. Other suggestions welcome. = Acknowledgements Mike Hall, for ideas and code that I borrowed from his 'filesystem' library. Park Heesob, for implementation and API ideas for the MS Windows version. Nobuyoshi Miyokawa, for adding the original FreeBSD and OS X support. = License Artistic 2.0 == Contributions Although this library is free, please consider having your company setup a gittip if used by your company professionally. http://www.gittip.com/djberg96/ = Copyright (C) 2003-2016 Daniel J. Berger All Rights Reserved = Warranty This library is provided "as is" and without any express or implied warranties, including, without limitation, the implied warranties of merchantability and fitness for a particular purpose. = Author Daniel J. Berger sys-filesystem-1.1.7/MANIFEST0000644000175000017500000000112112754302416014674 0ustar pravipravi* MANIFEST * CHANGES * Rakefile * README * sys-fileystem.gemspec * certs/djberg96_pub.pem * examples/example_stat.rb * lib/sys-filesystem.rb * lib/sys/filesystem.rb * lib/sys/unix/sys/filesystem.rb * lib/sys/unix/sys/filesystem/constants.rb * lib/sys/unix/sys/filesystem/functions.rb * lib/sys/unix/sys/filesystem/structs.rb * lib/sys/windows/sys/filesystem.rb * lib/sys/windows/sys/filesystem/constants.rb * lib/sys/windows/sys/filesystem/functions.rb * lib/sys/windows/sys/filesystem/helper.rb * test/test_sys_filesystem.rb * test/test_sys_filesystem_unix * test/test_sys_filesystem_windows sys-filesystem-1.1.7/Rakefile0000644000175000017500000000166112754302416015221 0ustar pravipravirequire 'rake' require 'rake/clean' require 'rake/testtask' CLEAN.include('**/*.gem', '**/*.rbc', '**/*.rbx') desc "Run the test suite" Rake::TestTask.new("test") do |t| if File::ALT_SEPARATOR t.libs << 'lib/windows' else t.libs << 'lib/unix' end t.warning = true t.verbose = true t.test_files = FileList['test/test_sys_filesystem.rb'] end desc "Run the example program" task :example do |t| sh "ruby -Ilib -Ilib/unix -Ilib/windows examples/example_stat.rb" end namespace :gem do desc "Build the sys-filesystem gem" task :create => [:clean] do |t| require 'rubygems/package' spec = eval(IO.read('sys-filesystem.gemspec')) spec.signing_key = File.join(Dir.home, '.ssh', 'gem-private_key.pem') Gem::Package.build(spec, true) end desc "Install the sys-filesystem gem" task :install => [:create] do file = Dir['*.gem'].first sh "gem install -l #{file}" end end task :default => :test sys-filesystem-1.1.7/test/0000755000175000017500000000000012754302416014527 5ustar pravipravisys-filesystem-1.1.7/test/test_sys_filesystem.rb0000644000175000017500000000025512754302416021177 0ustar pravipravi$LOAD_PATH.unshift File.dirname(File.expand_path(__FILE__)) if File::ALT_SEPARATOR require 'test_sys_filesystem_windows' else require 'test_sys_filesystem_unix' end sys-filesystem-1.1.7/test/test_sys_filesystem_unix.rb0000644000175000017500000001555712754302416022255 0ustar pravipravi#################################################################### # test_sys_filesystem_unix.rb # # Test case for the Sys::Filesystem.stat method and related stuff. # This test suite should be run via the 'rake test' task. #################################################################### require 'test-unit' require 'sys/filesystem' include Sys class TC_Sys_Filesystem_Unix < Test::Unit::TestCase def self.startup @@solaris = RbConfig::CONFIG['host_os'] =~ /solaris/i @@linux = RbConfig::CONFIG['host_os'] =~ /linux/i @@freebsd = RbConfig::CONFIG['host_os'] =~ /freebsd/i @@darwin = RbConfig::CONFIG['host_os'] =~ /darwin/i end def setup @dir = "/" @stat = Filesystem.stat(@dir) @mnt = Filesystem.mounts[0] @size = 58720256 @array = [] end def test_version assert_equal('1.1.7', Filesystem::VERSION) end def test_stat_path assert_respond_to(@stat, :path) assert_equal("/", @stat.path) end def test_stat_block_size assert_respond_to(@stat, :block_size) assert_kind_of(Fixnum, @stat.block_size) end def test_block_size_is_a_plausible_value assert_true(@stat.block_size >= 1024) assert_true(@stat.block_size <= 16384) end def test_stat_fragment_size assert_respond_to(@stat, :fragment_size) assert_kind_of(Fixnum, @stat.fragment_size) end def test_stat_blocks assert_respond_to(@stat, :blocks) assert_kind_of(Fixnum, @stat.blocks) end def test_stat_blocks_free assert_respond_to(@stat, :blocks_free) assert_kind_of(Fixnum, @stat.blocks_free) end def test_stat_blocks_available assert_respond_to(@stat, :blocks_available) assert_kind_of(Fixnum, @stat.blocks_available) end def test_stat_files assert_respond_to(@stat, :files) assert_kind_of(Fixnum, @stat.files) end def test_inodes_alias assert_respond_to(@stat, :inodes) assert_true(@stat.method(:inodes) == @stat.method(:files)) end def test_stat_files_free assert_respond_to(@stat, :files_free) assert_kind_of(Fixnum, @stat.files_free) end def test_stat_inodes_free_alias assert_respond_to(@stat, :inodes_free) assert_true(@stat.method(:inodes_free) == @stat.method(:files_free)) end def test_stat_files_available assert_respond_to(@stat, :files_available) assert_kind_of(Fixnum, @stat.files_available) end def test_stat_inodes_available_alias assert_respond_to(@stat, :inodes_available) assert_true(@stat.method(:inodes_available) == @stat.method(:files_available)) end def test_stat_filesystem_id assert_respond_to(@stat, :filesystem_id) assert_kind_of(Integer, @stat.filesystem_id) end def test_stat_flags assert_respond_to(@stat, :flags) assert_kind_of(Fixnum, @stat.flags) end def test_stat_name_max assert_respond_to(@stat, :name_max) assert_kind_of(Fixnum, @stat.name_max) end def test_stat_base_type omit_unless(@@solaris, "base_type test skipped except on Solaris") assert_respond_to(@stat, :base_type) assert_kind_of(String, @stat.base_type) end def test_stat_constants assert_not_nil(Filesystem::Stat::RDONLY) assert_not_nil(Filesystem::Stat::NOSUID) omit_unless(@@solaris, "NOTRUNC test skipped except on Solaris") assert_not_nil(Filesystem::Stat::NOTRUNC) end def test_stat_bytes_total assert_respond_to(@stat, :bytes_total) assert_kind_of(Numeric, @stat.bytes_total) end def test_stat_bytes_free assert_respond_to(@stat, :bytes_free) assert_kind_of(Numeric, @stat.bytes_free) end def test_stat_bytes_used assert_respond_to(@stat, :bytes_used) assert_kind_of(Numeric, @stat.bytes_used) end def test_stat_percent_used assert_respond_to(@stat, :percent_used) assert_kind_of(Float, @stat.percent_used) end def test_stat_expected_errors assert_raises(ArgumentError){ Filesystem.stat } end def test_numeric_methods_basic assert_respond_to(@size, :to_kb) assert_respond_to(@size, :to_mb) assert_respond_to(@size, :to_gb) assert_respond_to(@size, :to_tb) end def test_to_kb assert_equal(57344, @size.to_kb) end def test_to_mb assert_equal(56, @size.to_mb) end def test_to_gb assert_equal(0, @size.to_gb) end # Filesystem::Mount tests def test_mounts_with_no_block assert_nothing_raised{ @array = Filesystem.mounts } assert_kind_of(Filesystem::Mount, @array[0]) end def test_mounts_with_block assert_nothing_raised{ Filesystem.mounts{ |m| @array << m } } assert_kind_of(Filesystem::Mount, @array[0]) end def test_mounts_high_iteration assert_nothing_raised{ 1000.times{ @array = Filesystem.mounts } } end def test_mount_name assert_respond_to(@mnt, :name) assert_kind_of(String, @mnt.name) end def test_fsname_alias assert_respond_to(@mnt, :fsname) assert_true(@mnt.method(:fsname) == @mnt.method(:name)) end def test_mount_point assert_respond_to(@mnt, :mount_point) assert_kind_of(String, @mnt.mount_point) end def test_dir_alias assert_respond_to(@mnt, :dir) assert_true(@mnt.method(:dir) == @mnt.method(:mount_point)) end def test_mount_type assert_respond_to(@mnt, :mount_type) assert_kind_of(String, @mnt.mount_type) end def test_mount_options assert_respond_to(@mnt, :options) assert_kind_of(String, @mnt.options) end def test_opts_alias assert_respond_to(@mnt, :opts) assert_true(@mnt.method(:opts) == @mnt.method(:options)) end def test_mount_time assert_respond_to(@mnt, :mount_time) if @@solaris assert_kind_of(Time, @mnt.mount_time) else assert_nil(@mnt.mount_time) end end def test_mount_dump_frequency msg = 'dump_frequency test skipped on this platform' omit_if(@@solaris || @@freebsd || @@darwin, msg) assert_respond_to(@mnt, :dump_frequency) assert_kind_of(Fixnum, @mnt.dump_frequency) end def test_freq_alias assert_respond_to(@mnt, :freq) assert_true(@mnt.method(:freq) == @mnt.method(:dump_frequency)) end def test_mount_pass_number msg = 'pass_number test skipped on this platform' omit_if(@@solaris || @@freebsd || @@darwin, msg) assert_respond_to(@mnt, :pass_number) assert_kind_of(Fixnum, @mnt.pass_number) end def test_passno_alias assert_respond_to(@mnt, :passno) assert_true(@mnt.method(:passno) == @mnt.method(:pass_number)) end def test_mount_point_singleton assert_respond_to(Filesystem, :mount_point) assert_nothing_raised{ Filesystem.mount_point(Dir.pwd) } assert_kind_of(String, Filesystem.mount_point(Dir.pwd)) end def test_ffi_functions_are_private assert_false(Filesystem.methods.include?('statvfs')) assert_false(Filesystem.methods.include?('strerror')) end def teardown @dir = nil @stat = nil @array = nil end def self.shutdown @@solaris = nil @@linux = nil @@freebsd = nil @@darwin = nil end end sys-filesystem-1.1.7/test/test_sys_filesystem_windows.rb0000644000175000017500000001675512754302416022765 0ustar pravipravi#################################################################### # test_sys_filesystem_windows.rb # # Test case for the Sys::Filesystem.stat method and related stuff. # This should be run via the 'rake test' task. #################################################################### require 'test-unit' require 'sys/filesystem' require 'rbconfig' include Sys class TC_Sys_Filesystem_Windows < Test::Unit::TestCase def setup @dir = 'C:/' @stat = Filesystem.stat(@dir) @mount = Filesystem.mounts[0] @size = 58720256 @array = [] end test "version number is set to the expected value" do assert_equal('1.1.7', Filesystem::VERSION) end test "stat path works as expected" do assert_respond_to(@stat, :path) assert_equal("C:/", @stat.path) end test "stat block_size works as expected" do assert_respond_to(@stat, :block_size) assert_kind_of(Fixnum, @stat.block_size) end test "stat fragment_size works as expected" do assert_respond_to(@stat, :fragment_size) assert_nil(@stat.fragment_size) end test "stat blocks works as expected" do assert_respond_to(@stat, :blocks) assert_kind_of(Fixnum, @stat.blocks) end test "stat blocks_free works as expected" do assert_respond_to(@stat, :blocks_free) assert_kind_of(Fixnum, @stat.blocks_free) end test "stat blocks_available works as expected" do assert_respond_to(@stat, :blocks_available) assert_kind_of(Fixnum, @stat.blocks_available) end test "block stats return expected relative values" do assert_true(@stat.blocks >= @stat.blocks_free) assert_true(@stat.blocks_free >= @stat.blocks_available) end test "stat files works as expected" do assert_respond_to(@stat, :files) assert_nil(@stat.files) end test "stat inodes is an alias for files" do assert_alias_method(@stat, :inodes, :files) end test "stat files_free works as expected" do assert_respond_to(@stat, :files_free) assert_nil(@stat.files_free) end test "stat inodes_free is an alias for files_free" do assert_respond_to(@stat, :inodes_free) end test "stat files available works as expected" do assert_respond_to(@stat, :files_available) assert_nil(@stat.files_available) end test "stat inodes_available is an alias for files_available" do assert_alias_method(@stat, :inodes_available, :files_available) end test "stat filesystem_id works as expected" do assert_respond_to(@stat, :filesystem_id) assert_kind_of(Integer, @stat.filesystem_id) end test "stat flags works as expected" do assert_respond_to(@stat, :flags) assert_kind_of(Fixnum, @stat.flags) end test "stat name_max works as expected" do assert_respond_to(@stat, :name_max) assert_kind_of(Fixnum, @stat.name_max) end test "stat base_type works as expected" do assert_respond_to(@stat, :base_type) assert_kind_of(String, @stat.base_type) end test "stat bytes_total basic functionality" do assert_respond_to(@stat, :bytes_total) assert_kind_of(Numeric, @stat.bytes_total) end test "stat bytes_free basic functionality" do assert_respond_to(@stat, :bytes_free) assert_kind_of(Numeric, @stat.bytes_free) end test "stat bytes_used basic functionality" do assert_respond_to(@stat, :bytes_used) assert_kind_of(Numeric, @stat.bytes_used) end test "stat percent_used basic functionality" do assert_respond_to(@stat, :percent_used) assert_kind_of(Float, @stat.percent_used) end test "mount_point singleton method basic functionality" do assert_respond_to(Filesystem, :mount_point) assert_nothing_raised{ Filesystem.mount_point(Dir.pwd) } assert_kind_of(String, Filesystem.mount_point(Dir.pwd)) end test "mount_point singleton method returns expected value" do assert_equal("C:\\", Filesystem.mount_point("C:\\Users\\foo")) assert_equal("\\\\foo\\bar", Filesystem.mount_point("//foo/bar/baz")) end test "filesystem constants are defined" do assert_not_nil(Filesystem::CASE_SENSITIVE_SEARCH) assert_not_nil(Filesystem::CASE_PRESERVED_NAMES) assert_not_nil(Filesystem::UNICODE_ON_DISK) assert_not_nil(Filesystem::PERSISTENT_ACLS) assert_not_nil(Filesystem::FILE_COMPRESSION) assert_not_nil(Filesystem::VOLUME_QUOTAS) assert_not_nil(Filesystem::SUPPORTS_SPARSE_FILES) assert_not_nil(Filesystem::SUPPORTS_REPARSE_POINTS) assert_not_nil(Filesystem::SUPPORTS_REMOTE_STORAGE) assert_not_nil(Filesystem::VOLUME_IS_COMPRESSED) assert_not_nil(Filesystem::SUPPORTS_OBJECT_IDS) assert_not_nil(Filesystem::SUPPORTS_ENCRYPTION) assert_not_nil(Filesystem::NAMED_STREAMS) assert_not_nil(Filesystem::READ_ONLY_VOLUME) end test "stat singleton method defaults to root path if proviced" do assert_nothing_raised{ Filesystem.stat("C://Program Files") } end test "stat singleton method requires a single argument" do assert_raise(ArgumentError){ Filesystem.stat } assert_raise(ArgumentError){ Filesystem.stat(Dir.pwd, Dir.pwd) } end test "stat singleton method raises an error if path is not found" do assert_raise(Errno::ESRCH){ Filesystem.stat("C://Bogus//Dir") } end # Filesystem.mounts test "mounts singleton method basic functionality" do assert_respond_to(Filesystem, :mounts) assert_nothing_raised{ Filesystem.mounts } assert_nothing_raised{ Filesystem.mounts{} } end test "mounts singleton method returns the expected value" do assert_kind_of(Array, Filesystem.mounts) assert_kind_of(Filesystem::Mount, Filesystem.mounts[0]) end test "mounts singleton method works as expected when a block is provided" do assert_nil(Filesystem.mounts{}) assert_nothing_raised{ Filesystem.mounts{ |mt| @array << mt }} assert_kind_of(Filesystem::Mount, @array[0]) end test "mount name works as expected" do assert_respond_to(@mount, :name) assert_kind_of(String, @mount.name) end test "mount time works as expected" do assert_respond_to(@mount, :mount_time) assert_kind_of(Time, @mount.mount_time) end test "mount type works as expected" do assert_respond_to(@mount, :mount_type) assert_kind_of(String, @mount.mount_type) end test "mount point works as expected" do assert_respond_to(@mount, :mount_point) assert_kind_of(String, @mount.mount_point) end test "mount options works as expected" do assert_respond_to(@mount, :options) assert_kind_of(String, @mount.options) end test "mount pass_number works as expected" do assert_respond_to(@mount, :pass_number) assert_nil(@mount.pass_number) end test "mount frequency works as expected" do assert_respond_to(@mount, :frequency) assert_nil(@mount.frequency) end test "mounts singleton method does not accept any arguments" do assert_raise(ArgumentError){ Filesystem.mounts("C:\\") } end test "custom Fixnum#to_kb method works as expected" do assert_respond_to(@size, :to_kb) assert_equal(57344, @size.to_kb) end test "custom Fixnum#to_mb method works as expected" do assert_respond_to(@size, :to_mb) assert_equal(56, @size.to_mb) end test "custom Fixnum#to_gb method works as expected" do assert_respond_to(@size, :to_gb) assert_equal(0, @size.to_gb) end # FFI test "internal ffi functions are not public" do assert_false(Filesystem.methods.include?(:GetVolumeInformationA)) assert_false(Filesystem.instance_methods.include?(:GetVolumeInformationA)) end def teardown @array = nil @dir = nil @stat = nil @size = nil @mount = nil end end sys-filesystem-1.1.7/sys-filesystem.gemspec0000644000175000017500000000161412754302416020117 0ustar pravipravirequire 'rubygems' Gem::Specification.new do |spec| spec.name = 'sys-filesystem' spec.version = '1.1.7' spec.author = 'Daniel J. Berger' spec.email = 'djberg96@gmail.com' spec.homepage = 'https://github.com/djberg96/sys-filesystem' spec.summary = 'A Ruby interface for getting file system information.' spec.test_file = 'test/test_sys_filesystem.rb' spec.license = 'Artistic 2.0' spec.files = Dir['**/*'].reject{ |f| f.include?('git') } spec.cert_chain = Dir['certs/*'] spec.extra_rdoc_files = ['CHANGES', 'README', 'MANIFEST'] spec.add_dependency('ffi') spec.add_development_dependency('test-unit', '>= 2.5.0') spec.add_development_dependency('rake') spec.description = <<-EOF The sys-filesystem library provides a cross-platform interface for gathering filesystem information, such as disk space and mount point data. EOF end