noreply at rubyforge.org
2009-Jan-31 12:01 UTC
[Win32utils-devel] [ win32utils-Bugs-23746 ] File.size fails on locked file (and causes major rdebug wierdness)
Bugs item #23746, was opened at 2009-01-29 20:17
You can respond by visiting:
http://rubyforge.org/tracker/?func=detail&atid=411&aid=23746&group_id=85
Category: None
Group: None
Status: Open
Resolution: Accepted
Priority: 3
Submitted By: Montgomery Kosma (mkosma)
Assigned to: Nobody (None)
Summary: File.size fails on locked file (and causes major rdebug wierdness)
Initial Comment:
Running the following script fails in an ugly fashion. Note that the default
File.size does not fail (but it also returns an incorrect result, a negative
number).
#test.rb
require ''win32/file''
x = File.size(''c:/pagefile.sys'')
puts x
C:\docs\Prog\PSTTools>test.rb
c:/ruby/lib/ruby/gems/1.8/gems/win32-file-stat-1.3.2/lib/win32/file/stat.rb:586:
in `get_file_type'': unknown error - The process cannot access the file
because it is being used by another process. (SystemCallError)
from
c:/ruby/lib/ruby/gems/1.8/gems/win32-file-stat-1.3.2/lib/win32/file/stat.rb:58:in
`initialize''
from
c:/ruby/lib/ruby/gems/1.8/gems/win32-file-0.6.0/lib/win32/file.rb:669:in
`new''
from
c:/ruby/lib/ruby/gems/1.8/gems/win32-file-0.6.0/lib/win32/file.rb:669:in
`size''
from C:/docs/Prog/PSTTools/test.rb:3
So I tried to dig into the win32-file source to see where it''s failing
-- a size command really shouldn''t need to lock the file. The really
puzzling thing is that I cannot successfully run rdebug on this. Even if I set
a breakpoint before the call to File.size, rdebug errors out before it arrives.
I''m not skilled enough (yet) to determine if this is related to the
win32-size bug, or a problem with rdebug (ver 0.10.3). Here''s what
happens:
C:\docs\Prog\PSTTools>rdebug test.rb
C:/docs/Prog/PSTTools/test.rb:1
require ''win32/file''
(rdb:1) list
[-4, 5] in C:/docs/Prog/PSTTools/test.rb
=> 1 require ''win32/file''
2
3 x = File.size(''c:/pagefile.sys'')
4 puts x
5
(rdb:1) b 3
Breakpoint 1 file C:/docs/Prog/PSTTools/test.rb, line 3
(rdb:1) n
INTERNAL ERROR!!! no implicit conversion from nil to integer
c:/ruby/lib/ruby/1.8/pathname.rb:269:in `[]''
c:/ruby/lib/ruby/1.8/pathname.rb:269:in `chop_basename''
c:/ruby/lib/ruby/1.8/pathname.rb:322:in `cleanpath_aggressive''
c:/ruby/lib/ruby/1.8/pathname.rb:310:in `cleanpath''
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-0.10.3/cli/ruby-debug/processor.rb:93:in
`canonic_file''
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-0.10.3/cli/ruby-debug/processor.rb:98:in
`print_location_and_text''
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-0.10.3/cli/ruby-debug/processor.rb:243:in
`process_commands''
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-0.10.3/cli/ruby-debug/processor.rb:171:in
`__at_line''
(eval):5:in `at_line''
(eval):3:in `synchronize''
(eval):3:in `at_line''
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-base-0.10.3-x86-mswin32/lib/ruby-debug-base.rb:54:in
`at_line''
C:/docs/Prog/PSTTools/test.rb:3
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-0.10.3/bin/rdebug:125:in
`debug_load''
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-0.10.3/bin/rdebug:125:in
`debug_program''
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-0.10.3/bin/rdebug:412
c:/ruby/bin/rdebug:19:in `load''
c:/ruby/bin/rdebug:19
c:/ruby/lib/ruby/gems/1.8/gems/win32-file-stat-1.3.2/lib/win32/file/stat.rb:586:in
`get_file_type''
c:/ruby/lib/ruby/gems/1.8/gems/win32-file-stat-1.3.2/lib/win32/file/stat.rb:58:in
`initialize''
c:/ruby/lib/ruby/gems/1.8/gems/win32-file-0.6.0/lib/win32/file.rb:669:in
`new''
c:/ruby/lib/ruby/gems/1.8/gems/win32-file-0.6.0/lib/win32/file.rb:669:in
`size''
C:/docs/Prog/PSTTools/test.rb:3
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-0.10.3/bin/rdebug:125:in
`debug_load''
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-0.10.3/bin/rdebug:125:in
`debug_program''
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-0.10.3/bin/rdebug:412
c:/ruby/bin/rdebug:19:in `load''
c:/ruby/bin/rdebug:19
Uncaught exception: unknown error - The process cannot access the file because
it is being used by another process.
----------------------------------------------------------------------
>Comment By: Daniel Berger (djberg96)
Date: 2009-01-31 05:01
Message:
That will work, thanks. The problem with that approach, however, is that it
would result in having two separate implementations - one for File.size, and one
for File::Stat#size.
The also noticed that GetFileAttributes fails on that file, so it''s
double trouble.
Maybe I should replace the Win32::File::Stat implementation with one that uses
FindFirstFile, since the WIN32_FIND_DATA struct stores attribute information as
well.
Dan
----------------------------------------------------------------------
Comment By: Park Heesob (phasis68)
Date: 2009-01-30 07:30
Message:
There are two issues in this error.
First, the Standard API function CreateFile cannot open file locked by
"System" such as "pagefile.sys".
We need other workaround to handle system locked file.
Second, the complex stat call is not needed to get only the file size.
Here is a usable size method for win32-file:
def size(file)
# File::Stat.new(file).size
buffer = 0.chr * 512
h = FindFirstFile(file,buffer)
if h == INVALID_HANDLE_VALUE
raise SystemCallError,get_last_error()
end
FindClose(h)
(buffer[28,4].unpack(''L'').first << 32) +
buffer[32,4].unpack(''L'').first
end
Regards,
Park Heesob
----------------------------------------------------------------------
You can respond by visiting:
http://rubyforge.org/tracker/?func=detail&atid=411&aid=23746&group_id=85
noreply at rubyforge.org
2009-Jan-31 13:40 UTC
[Win32utils-devel] [ win32utils-Bugs-23746 ] File.size fails on locked file (and causes major rdebug wierdness)
Bugs item #23746, was opened at 2009-01-30 12:17
You can respond by visiting:
http://rubyforge.org/tracker/?func=detail&atid=411&aid=23746&group_id=85
Category: None
Group: None
Status: Open
Resolution: Accepted
Priority: 3
Submitted By: Montgomery Kosma (mkosma)
Assigned to: Nobody (None)
Summary: File.size fails on locked file (and causes major rdebug wierdness)
Initial Comment:
Running the following script fails in an ugly fashion. Note that the default
File.size does not fail (but it also returns an incorrect result, a negative
number).
#test.rb
require ''win32/file''
x = File.size(''c:/pagefile.sys'')
puts x
C:\docs\Prog\PSTTools>test.rb
c:/ruby/lib/ruby/gems/1.8/gems/win32-file-stat-1.3.2/lib/win32/file/stat.rb:586:
in `get_file_type'': unknown error - The process cannot access the file
because it is being used by another process. (SystemCallError)
from
c:/ruby/lib/ruby/gems/1.8/gems/win32-file-stat-1.3.2/lib/win32/file/stat.rb:58:in
`initialize''
from
c:/ruby/lib/ruby/gems/1.8/gems/win32-file-0.6.0/lib/win32/file.rb:669:in
`new''
from
c:/ruby/lib/ruby/gems/1.8/gems/win32-file-0.6.0/lib/win32/file.rb:669:in
`size''
from C:/docs/Prog/PSTTools/test.rb:3
So I tried to dig into the win32-file source to see where it''s failing
-- a size command really shouldn''t need to lock the file. The really
puzzling thing is that I cannot successfully run rdebug on this. Even if I set
a breakpoint before the call to File.size, rdebug errors out before it arrives.
I''m not skilled enough (yet) to determine if this is related to the
win32-size bug, or a problem with rdebug (ver 0.10.3). Here''s what
happens:
C:\docs\Prog\PSTTools>rdebug test.rb
C:/docs/Prog/PSTTools/test.rb:1
require ''win32/file''
(rdb:1) list
[-4, 5] in C:/docs/Prog/PSTTools/test.rb
=> 1 require ''win32/file''
2
3 x = File.size(''c:/pagefile.sys'')
4 puts x
5
(rdb:1) b 3
Breakpoint 1 file C:/docs/Prog/PSTTools/test.rb, line 3
(rdb:1) n
INTERNAL ERROR!!! no implicit conversion from nil to integer
c:/ruby/lib/ruby/1.8/pathname.rb:269:in `[]''
c:/ruby/lib/ruby/1.8/pathname.rb:269:in `chop_basename''
c:/ruby/lib/ruby/1.8/pathname.rb:322:in `cleanpath_aggressive''
c:/ruby/lib/ruby/1.8/pathname.rb:310:in `cleanpath''
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-0.10.3/cli/ruby-debug/processor.rb:93:in
`canonic_file''
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-0.10.3/cli/ruby-debug/processor.rb:98:in
`print_location_and_text''
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-0.10.3/cli/ruby-debug/processor.rb:243:in
`process_commands''
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-0.10.3/cli/ruby-debug/processor.rb:171:in
`__at_line''
(eval):5:in `at_line''
(eval):3:in `synchronize''
(eval):3:in `at_line''
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-base-0.10.3-x86-mswin32/lib/ruby-debug-base.rb:54:in
`at_line''
C:/docs/Prog/PSTTools/test.rb:3
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-0.10.3/bin/rdebug:125:in
`debug_load''
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-0.10.3/bin/rdebug:125:in
`debug_program''
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-0.10.3/bin/rdebug:412
c:/ruby/bin/rdebug:19:in `load''
c:/ruby/bin/rdebug:19
c:/ruby/lib/ruby/gems/1.8/gems/win32-file-stat-1.3.2/lib/win32/file/stat.rb:586:in
`get_file_type''
c:/ruby/lib/ruby/gems/1.8/gems/win32-file-stat-1.3.2/lib/win32/file/stat.rb:58:in
`initialize''
c:/ruby/lib/ruby/gems/1.8/gems/win32-file-0.6.0/lib/win32/file.rb:669:in
`new''
c:/ruby/lib/ruby/gems/1.8/gems/win32-file-0.6.0/lib/win32/file.rb:669:in
`size''
C:/docs/Prog/PSTTools/test.rb:3
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-0.10.3/bin/rdebug:125:in
`debug_load''
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-0.10.3/bin/rdebug:125:in
`debug_program''
c:/ruby/lib/ruby/gems/1.8/gems/ruby-debug-0.10.3/bin/rdebug:412
c:/ruby/bin/rdebug:19:in `load''
c:/ruby/bin/rdebug:19
Uncaught exception: unknown error - The process cannot access the file because
it is being used by another process.
----------------------------------------------------------------------
>Comment By: Park Heesob (phasis68)
Date: 2009-01-31 22:40
Message:
Win32::File::Stat implementation with FindFirst would be better.
If you really want to keep the current implementation, you can get the handle of
system locked file by the undocumented NtQuerySystemInformation API instead of
CreateFile. Refer to http://forum.sysinternals.com/forum_posts.asp?TID=3577
Regards,
Park Heesob
----------------------------------------------------------------------
Comment By: Daniel Berger (djberg96)
Date: 2009-01-31 21:01
Message:
That will work, thanks. The problem with that approach, however, is that it
would result in having two separate implementations - one for File.size, and one
for File::Stat#size.
The also noticed that GetFileAttributes fails on that file, so it''s
double trouble.
Maybe I should replace the Win32::File::Stat implementation with one that uses
FindFirstFile, since the WIN32_FIND_DATA struct stores attribute information as
well.
Dan
----------------------------------------------------------------------
Comment By: Park Heesob (phasis68)
Date: 2009-01-30 23:30
Message:
There are two issues in this error.
First, the Standard API function CreateFile cannot open file locked by
"System" such as "pagefile.sys".
We need other workaround to handle system locked file.
Second, the complex stat call is not needed to get only the file size.
Here is a usable size method for win32-file:
def size(file)
# File::Stat.new(file).size
buffer = 0.chr * 512
h = FindFirstFile(file,buffer)
if h == INVALID_HANDLE_VALUE
raise SystemCallError,get_last_error()
end
FindClose(h)
(buffer[28,4].unpack(''L'').first << 32) +
buffer[32,4].unpack(''L'').first
end
Regards,
Park Heesob
----------------------------------------------------------------------
You can respond by visiting:
http://rubyforge.org/tracker/?func=detail&atid=411&aid=23746&group_id=85