dll locking problem

J

joseph2000

Hi,

I'd like to ask you for some ideas how to solve problem I currently have.
The problem is as follows:

we have a component which is integrated with w Windows Explorer. From time
to time we need to make an update, which is performed on client machines.
And here the problem appears - all the assemblies used by the component are
being locked by the explorer process, so we need to unlock them somehow.
Till now we have used dirty approach which involved killing the explorer
process and then trying to update the component assemblies. Of course after
that the explorer was started again.
Unfortunately very often the assemblies are used not only by the Windows
Explorer process but by another processess as well - then update fails.

What I'd like to do is to being able to perform similar actions to these
offered by Unlocker 1.8.5 program: find all processes that are using libraries
in given folder, unlock/unload them and then perform assemblies update.
This is my idea what should I do but I don't know how. Could you help me,
please?

On the other hand maybe you have another ideas how to solve the problem without
building a 10 pounds hammer to kill a small bug.

Thanks in advance,
Wojtek
 
N

Nicholas Paldino [.NET/C# MVP]

Wojtek,

Generally speaking, using .NET for explorer extensions (shell views and
whatnot) is not a good idea, for this reason, and .NET runtime version
reasons as well (you can only have one version of the runtime in a process,
if you have multiple plugins which use different versions of the runtime,
what do you do?).

If you must use .NET assemblies in your extensions to explorer, then you
are going to have to use application domains to host your assemblies in.
When you need an update, you can kill the app domains, update the
assemblies, and then create new app domains and access your types through
that.
 
W

Walter Wang [MSFT]

Hi Wojtek,

As Nicholas pointed out, creating shell extension and hosting in
explorer.exe with managed code is not recommended and supported:

#Windows Shell: Create Namespace Extensions for Windows Explorer with the
NET Framework -- MSDN Magazine, January 2004
http://msdn.microsoft.com/msdnmag/issues/04/01/WindowsShell/default.aspx
<quote>
[ Editor's Update - 6/23/2006: Because shell extensions are loaded into
arbitrary processes and because managed code built against one version of
the runtime may not run in a process running an earlier version of the
runtime, Microsoft recommends against writing managed shell extensions and
does not consider them a supported scenario.]
</quote>


On the other hand, if your question is a general one about how to find
which process is locking a specific file, basically you need to use psapi
to enumerate open handles by each process and see if it's locking a
specified file.

If you're looking for a quick solution, maybe you can delegate to
handle.exe and parse the output:

#Handle v3.20
http://www.microsoft.com/technet/sysinternals/utilities/handle.mspx

Regards,
Walter Wang ([email protected], remove 'online.')
Microsoft Online Community Support

==================================================
When responding to posts, please "Reply to Group" via your newsreader so
that others may learn and benefit from your issue.
==================================================

This posting is provided "AS IS" with no warranties, and confers no rights.
 
J

joseph2000

Hello Walter,

Thanks for the information. As you suggested I have used "psapi" approach:
first I'm enumerating all processes and then looking if there is any process
which is using libraries I'm going to update. If there is such a process
I'm killing it.
One of the processes is of course explorer.exe, which is obvious. From my
point of view killing the the shell process, should free all loaded shell
extensions, including mine. It works that way quite often but in not all
cases. Sometimes even if explorer is not working anymore I cannot update
libraries I want to update because I'm receiving an info (exception) that
a given library is being used by another process. I must add there is no
other process which is using the libraries - I was checking it by using three
different tools: ProcessExplorer, Handle.exe and Unlocker. It seems that
sometimes when explorer.exe is killed not all resources are unloaded, especially
my shell extension libraries.
What should I do to unload my shell extension assemblies when the explorer.exe
process is killed? Is there any method to force this programmatically?
On the other hand I can add special functionality to my "updater" - when
shell libraries cannot be updated in runtime I'm going to use the "inuse"
tool (see http://support.microsoft.com/kb/228930). Of course it requires
computer restart. I wanted to update the shell extension libraries without
need of restarting user computer but if there is not a chance to do that,
because of problems with unlocking, I'm going to follow the path however
I'm not very satisfied with this approach.

Any ideas what to do to update shell extension libraries without using inuse
tool or restarting system are very welcome.

Best regards,
Wojtek

Hi Wojtek,

As Nicholas pointed out, creating shell extension and hosting in
explorer.exe with managed code is not recommended and supported:

#Windows Shell: Create Namespace Extensions for Windows Explorer with
the
.NET Framework -- MSDN Magazine, January 2004
http://msdn.microsoft.com/msdnmag/issues/04/01/WindowsShell/default.as
px
<quote>
[ Editor's Update - 6/23/2006: Because shell extensions are loaded
into
arbitrary processes and because managed code built against one version
of
the runtime may not run in a process running an earlier version of the
runtime, Microsoft recommends against writing managed shell extensions
and
does not consider them a supported scenario.]
</quote>
On the other hand, if your question is a general one about how to find
which process is locking a specific file, basically you need to use
psapi to enumerate open handles by each process and see if it's
locking a specified file.

If you're looking for a quick solution, maybe you can delegate to
handle.exe and parse the output:

#Handle v3.20
http://www.microsoft.com/technet/sysinternals/utilities/handle.mspx
Regards,
Walter Wang ([email protected], remove 'online.')
Microsoft Online Community Support
==================================================
When responding to posts, please "Reply to Group" via your newsreader
so
that others may learn and benefit from your issue.
==================================================
This posting is provided "AS IS" with no warranties, and confers no
rights.
 
W

Walter Wang [MSFT]

Hi Wojtek,

Please understand using .NET to create shell extension is really not
supported.

On the other hand, my wild guess is that simply killing explorer.exe will
cause it automatically restarted again, there's no guarantee if you could
update your assembly before it's restarted again.

Not a direct answer to your requirement of "programmatically", there's a
manual way to exit explorer.exe process completely (it will not be
restarted automatically):

* On Vista, bring up the start menu, on the empty space, hold-down
Ctrl+Shift and right-click the mouse button, it will popup a menu to let
you "exit explorer"
* On XP or 2003 (probably 2000 but I haven't tested): bring up the
"shutdown" dialog, hold-down Ctrl+Shift+Alt and click "Cancel".

This is usually to help you debug shell extensions more easily.


Regards,
Walter Wang ([email protected], remove 'online.')
Microsoft Online Community Support

==================================================
When responding to posts, please "Reply to Group" via your newsreader so
that others may learn and benefit from your issue.
==================================================

This posting is provided "AS IS" with no warranties, and confers no rights.
 
J

joseph2000

Hello Walter,

I really understand that using .NET to creat shell extension is not supported
by Microsoft. Unfortunately it is too late to rewrite the extension in C++
however I must say that I don't have problems with the extension itself.
The problem is with updating the extension assemblies in runtime. What I'd
like to know right now is if it is possible that when killing the explorer.exe
process the .NET extension assemblies sometimes are not unloaded at all.
If it is possible why it happens and how to avoid such a situation?
On the other hand to kill the explorer process completely you need to execute
the following command from batch:

TASKKILL /F /IM explorer.exe

where param /F means that a given process must be terminated forcefully and
the /IM switch specifies the image name of the process that must be terminated.

Best regards,
Wojtek
 
W

Walter Wang [MSFT]

Hi Wojtek,

Remember you can always use Process Explorer from sysinternals to find
which process is loading your DLL. Maybe there's other processes still
using your file after explorer.exe is killed.


Regards,
Walter Wang ([email protected], remove 'online.')
Microsoft Online Community Support

==================================================
When responding to posts, please "Reply to Group" via your newsreader so
that others may learn and benefit from your issue.
==================================================

This posting is provided "AS IS" with no warranties, and confers no rights.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Similar Threads


Top