how to force Thread.Abort() to Abort ?

  • Thread starter Thread starter Andy Fish
  • Start date Start date
A

Andy Fish

Hi,

I am using COM interop to invoke MS word from my .net app. If word pops up a
dialog box, my thread obviously hangs until the dialog is answered.

Here's the problem: because the app is running on a server, there is nobody
there to answer the dialog, so I have another thread that calls Abort() on
the first thread in the event that the operation doesn't complete within a
certain amount of time.

Unfortunately, whilst the call to Thread.Abort() works, the dialog box stays
up and the subsequent Thread.Join() hangs until the dialog is cancelled.

Is there any way round this behaviour? This isn't going to happen very often
so I don't care how inefficient it is, but it's got to run on an unattended
server so I can't afford to have my app get stuck forever.

TIA

Andy
 
The abort does not actually get delivered to the managed thread until it
returns from the unmanaged call. There is no way to get around that
behavior.

You could try running the interop call in a separate appdomain, and then
unload the appdomain instead of using an abort. I've observed that the CLR
will go to greater lengths to unload frozen threads when unloading an
appdomain then when you simply call abort.

Another option is to run it in a totally separate process and then unload
the process. You could use remoting between processes to send data
back-and-forth between the main process and the helper process.

In short, there is no good way to shutdown a thread frozen in an unmanaged
call.
 
A user dialog on a server indicates either poor design or usage of a
component outside of its intended environment. Which of the two can you
repair?

--
Regards,
Alvin Bruney

Shameless Author plug
The Microsoft Office Web Components Black Book with .NET
http://tinyurl.com/27cok
 
If your service runs without "desktop interaction" enabled, it's impossible
to get around this issue. If your service runs with desktop interaction
enabled (it shouldn't) you can try to simulate Keyboard input using
SendInput (you have to make sure the dialog got focus), or you can try to
get the Window handle of the Dialog and use SendMessage to simulate a
key-press. The problem of course is "what dialog is there actually
displayed?", you won't press OK on any possible dialog don't you?

This is one of the many reasons you shouldn't try to automate "Office
applications" (or any other interactive application) on a server.

Willy.
 
Alvin Bruney said:
A user dialog on a server indicates either poor design or usage of a
component outside of its intended environment. Which of the two can you
repair?

I think it's the latter, but I don't see any other option.

I'm trying to convert a word format document to WordProcessingML. In this
case the user has uploaded a document with a password and word is asking for
the password.

AFAIK there is no other way of converting a .doc to XML other than using
winword.exe. This is the real problem - MS are pushing WordProcessingML as a
way of processing word documents on the server but it does not offer any
server-side solution to convert to and from .doc format.

From what I can see there is no way to detect if the doc is
password-protected without opening it, and no way to stop word putting up
the dialog.

any other more "out-of-the-box" suggestions would be welcome

Andy
 
In essence what you are witnessing is one of the reasons why they warn you that Office is not suitable for server side use (theres lots of other reasons too like threading throughput). IIRC correctly, the WordML schema has now been published and generating WordML would be a more scaleable and robust solution than trying to automate word on the server

Regards

Richard Blewett - DevelopMentor
http://www.dotnetconsult.co.uk/weblog
http://www.dotnetconsult.co.uk

The abort does not actually get delivered to the managed thread until it
returns from the unmanaged call. There is no way to get around that
behavior.

You could try running the interop call in a separate appdomain, and then
unload the appdomain instead of using an abort. I've observed that the CLR
will go to greater lengths to unload frozen threads when unloading an
appdomain then when you simply call abort.

Another option is to run it in a totally separate process and then unload
the process. You could use remoting between processes to send data
back-and-forth between the main process and the helper process.

In short, there is no good way to shutdown a thread frozen in an unmanaged
call.



Andy Fish said:
Hi,

I am using COM interop to invoke MS word from my .net app. If word pops up
a dialog box, my thread obviously hangs until the dialog is answered.

Here's the problem: because the app is running on a server, there is
nobody there to answer the dialog, so I have another thread that calls
Abort() on the first thread in the event that the operation doesn't
complete within a certain amount of time.

Unfortunately, whilst the call to Thread.Abort() works, the dialog box
stays up and the subsequent Thread.Join() hangs until the dialog is
cancelled.

Is there any way round this behaviour? This isn't going to happen very
often so I don't care how inefficient it is, but it's got to run on an
unattended server so I can't afford to have my app get stuck forever.

TIA

Andy



--
No virus found in this incoming message.
Checked by AVG Anti-Virus.
Version: 7.0.300 / Virus Database: 265.7.1 - Release Date: 19/01/2005



[microsoft.public.dotnet.languages.csharp]
 
Thanks Richard, you understand my problem exactly !!

My application makes extensive use of WordML, and is a model of exactly the
type of thing MS want people to use WordML for. Unfortunately, when the user
uploads a document, I need to convert it from .doc format to WordML so get
the process started. Microsoft doesn't seem to have thought of this part of
it, so the only option open to me is to automate Word.


Richard Blewett said:
In essence what you are witnessing is one of the reasons why they warn you
that Office is not suitable for server side use (theres lots of other
reasons too like threading throughput). IIRC correctly, the WordML schema
has now been published and generating WordML would be a more scaleable and
robust solution than trying to automate word on the server

Regards

Richard Blewett - DevelopMentor
http://www.dotnetconsult.co.uk/weblog
http://www.dotnetconsult.co.uk

The abort does not actually get delivered to the managed thread until it
returns from the unmanaged call. There is no way to get around that
behavior.

You could try running the interop call in a separate appdomain, and then
unload the appdomain instead of using an abort. I've observed that the CLR
will go to greater lengths to unload frozen threads when unloading an
appdomain then when you simply call abort.

Another option is to run it in a totally separate process and then unload
the process. You could use remoting between processes to send data
back-and-forth between the main process and the helper process.

In short, there is no good way to shutdown a thread frozen in an unmanaged
call.



Andy Fish said:
Hi,

I am using COM interop to invoke MS word from my .net app. If word pops
up
a dialog box, my thread obviously hangs until the dialog is answered.

Here's the problem: because the app is running on a server, there is
nobody there to answer the dialog, so I have another thread that calls
Abort() on the first thread in the event that the operation doesn't
complete within a certain amount of time.

Unfortunately, whilst the call to Thread.Abort() works, the dialog box
stays up and the subsequent Thread.Join() hangs until the dialog is
cancelled.

Is there any way round this behaviour? This isn't going to happen very
often so I don't care how inefficient it is, but it's got to run on an
unattended server so I can't afford to have my app get stuck forever.

TIA

Andy



--
No virus found in this incoming message.
Checked by AVG Anti-Virus.
Version: 7.0.300 / Virus Database: 265.7.1 - Release Date: 19/01/2005



[microsoft.public.dotnet.languages.csharp]
 
Hmmm - you are in a bad place basically. Can you get the user to upload in WordML format in the first place? Assuming they do it via http, maybe you could check the content type of the PUT and if it is not text/xml return an error to them so they know what they have done wrong

Regards

Richard Blewett - DevelopMentor
http://www.dotnetconsult.co.uk/weblog
http://www.dotnetconsult.co.uk

Thanks Richard, you understand my problem exactly !!

My application makes extensive use of WordML, and is a model of exactly the
type of thing MS want people to use WordML for. Unfortunately, when the user
uploads a document, I need to convert it from .doc format to WordML so get
the process started. Microsoft doesn't seem to have thought of this part of
it, so the only option open to me is to automate Word.
 
Unfortunately that's not an option from a business perspective. we'll have
to have some kind of solution even if it comes down to a robot arm which
presses the escape key every 20 seconds ;-))

current options I'm looking at are (a) using SendKeys; or (b) killing every
copy of winword.exe on the machine. Not what you'd call elegant

Andy
 
Andy Fish said:
Unfortunately that's not an option from a business perspective. we'll have
to have some kind of solution even if it comes down to a robot arm which
presses the escape key every 20 seconds ;-))

current options I'm looking at are (a) using SendKeys; or (b) killing
every copy of winword.exe on the machine. Not what you'd call elegant

Andy

Did you look for alternatives that don't require Word at all?
Following a just a few I have used for asp based applications, guess they
offer the same for asp.net too.

http://www.polarsoftware.com/products/converter/index.asp

http://officewriter.softartisans.com/officewriter-253.aspx

Willy.
 
The comments about dealing with Word.Exe (a nearly 12MB executable!) as a
COM Server are on the money.
Several vendors (one to look at is "Aspose") have 100% managed code class
libraries that can talk "word", "Excel" and so on.

They aren't cheap, but you won't be left with 123 instances of WORD.EXE in
Task Manager...

Good luck!
 
I've looked at aspose but unfortunately they don't support WordML yet.

there is something called PolarConverver which purports to do exactly what I
want, but unfortunately there are too many of my test documents it barfed
on.
 
FWIW here was my solution:

1. find the process ID of the winword.exe you are using. This is not easy
with COM so the only way I could think of is to enumerate all winword.exe
processes just before creating the COM object and then again afterwards.
Compare the two lists and new one is the OOP server you're connected to

2. afer calling thread.abort(), if thread.join() doesn't return in a few
seconds, kill the winword.exe process and call thread.join() again

it's not elegant but it works for me.
 
Back
Top