I was going to say that you could use a named Mutex, but given the multi-threaded beast that is ASP.Net, you wouldn't be guaranteed that the owning thread would be the same thread that releases it. That would likely cause problems. SO...
The easiest method would probably be to use the file system.
Have the console app instantiate a FileSystemWatcher to monitor a directory that both processes can access for changes and wire up an event handler for the Created event, something like this:
internal static bool ShutDownRequested { get ; set ; }
private static void OnCreated( object sender , FileSystemEventArgs fileSystemEventArgs )
{
FileSystemWatcher watcher = (FileSystemWatcher) sender ;
ShutDownRequested = true ;
File.Delete( fileSystemEventArgs.FullPath ) ;
watcher.Created -= OnCreated ;
}
static void Main()
{
using ( FileSystemWatcher watcher = new FileSystemWatcher( @"\some\common\directory" , "foobar.shutdown.requested" ) )
{
watcher.Created += OnCreated;
while ( !ShutDownRequested )
{
DoSomethingUseful() ;
}
}
return ;
}
When you want to shut down the console app, just create the file the console app is expecting. The console app's event handler catches the event on a worker thread and can then set the global shutdown flag so the main thread can gracefully shutdown at the first opportune time, or the event handler can simply invoke Environment.Exit(int)
and force it down. Don't forget to tidy things up by deleting the sentinel file after it's done its job (it's the only polite thing to do).
That's what I'd do, but then, I'm not big on over-thinking things.
On overthinking, you can use a named event in a similar fashion. In your ASP.Net service, created a named event that's initially unsignalled:
// start console app
EventWaitHandle wh = new EventWaitHandle(false, EventResetMode.ManualReset,"foobar.shutdown.signal");
SpawnConsoleApp() ;
Then, when it's time to shut down the console app:
// shutdown time
wh.Set() ;
(Don't forget to stow the wait handle some place safe)
In your console app, you need to periodically check for a signal:
static void Main()
{
EventWaitHandle wh = EventWaitHandle.OpenExisting( "foobar.shutdown.signal" ) ;
while( !wh.WaitOne(0) )
{
DoSomethingUseful() ;
}
wh.Set() ; // acknowledge the signal
return ;
}