-
Notifications
You must be signed in to change notification settings - Fork 77
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
RootStorage.ReadOnly() cannot open a file being used by another process #260
Comments
Perhaps this is more of a documentation/sample thing, basically only two modes are supported (and have unit tests):
The omission of the FileShare parameter is somewhat deliberate, since SWMR etc. is not supported (AFAIK it also wasn't supported in v2.3/2.4 even if it was allowed by the API). i.e. FileAccess.ReadWrite with anything but FileShare.None should throw until/unless SWMR gets implemented. |
Perhaps this should be closed as a duplicate of #236? |
I have documents that are locked when opened in an application and I'm using openmcdf to read the documents in a separate process. #236 was tagged as an enhancement. I raised this to cover the loss of functionality. |
Right, but what I'm trying to say is that that situation isn't supported, either in 2.3/4 or 3.0. IMHO this isn't so much a loss of functionality as it is a bug in 2.3/4 that it even allows you to try... The other application might alter the file at any given moment, and both 2.3/4 and 3.0 assume they have exclusive access (2.x even more so than 3) - the only difference is that 3.0 prevents the caller from doing it since it's dangerous. Can I ask what the other application is, and/or whether you have control of it to do something else? If you still really really want to do it despite knowing that it isn't supported and might crash etc., then you can always open the file whichever way you want and pass it to one of the stream-based constructors. There's nothing that can be done to prevent it being misused in that way, but it does raise an interesting point... maybe the 3.0 constructors shouldn't actually allow streams to be passed in directly, but only accept something that can enforce locking similar to ILockBytes (an oversight on my part that people wouldn't try and use it in this way). |
As an additional hint, if you just want to quickly open and close a file, then depending on what the other process is doing, then you might be able to do something like:
Given that the other process hasn't prevented sharing, I think that it's likely to work OK (on Windows at least - locking on other operating systems is generally advisory only) |
Also, thanks very much for reporting this - although the response might not have been what you wanted to hear, it is great and valuable feedback, and I'll have a think about if/how the API should be changed accordingly. |
I'm working on add-ins for CAD programs so I have full control of the file reading/writing but there are times when I want to read the file properties directly. Thank you for your help. I'll pass the filestream into the constructor and am happy to close this issue. |
Oh, it's OK to keep the issue open for now. There are things we might be able to do or change... But I think if we're opening a file that is also open for write in another process then we should probably also lock the stream. Without implementing SWMR properly, this likely equates to locking the whole file, even just for reading it. So, we could consider this ticket to be the "multiple reader" part of SWMR (while some other implementation does the writing), and that could be done independently of the "single writer" part. |
@conormcg94 How did you get on with this one? Did the CAD application function OK with the file locks? |
Yes the file locks work although I still have to open the filestream with FileShare.ReadWrite. |
The structured storage project doesn't really do very much - it's just some wrappers around P/Invokes from CsWin32 - you're welcome to copy it and do what you want with it. It's Windows specific, so not really in line with the goals of this project exactly. If you're OK with it being Windows specific then you could just use the Win32/COM API without really needing OpenMcdf. It raises an interesting point though, whether the StructuredStorage reference has value as a NuGet package in itself... I'm curious about what you mean by the CAD document providing an IStorage interface? |
The cad application has a method for opening sub-storage within the CAD document, it returns a pointer to an object which implements win32 IStorage. The structured storage project is useful for creating an System.IO.Stream wrapper to pass into openmcdf RootStorage |
Calling RootStorage.ReadOnly() throws an IO Exception when trying to read a file used in another process.
Whereas V2.4 opened the file for reading as default.
This can be resolved by setting the FileShare parameter to ReadWrite for System.IO.File.Open().
The text was updated successfully, but these errors were encountered: