February 08, 2005
Hello,

Can we have a platform-independent way to trap the CTRL-C signal for D programs? I'm writing a server application that needs to close nicely on a CTRL-C under Linux.

Also, the static ~this() of modules does not get executed on a CTRL-C, and the
garbage collector is left undestroyed (presumably the memory is freed by the OS
upon program close).

A temporary fix would be to define export functions of the signal() routines
under Linux (which are not in the Phobos linux declaration modules, and which
should be) and call them with extern (C) defined signal-handler functions.

Regards,
James Dunne
February 08, 2005
Would you want to have some kind of Ctrl-C handler registration, whereby an object implementing ICtrlCHandler, or some such, would be passed into a registration function. If the user requires, the implementing instance would have access to state within the (main) thread of execution, such that it could take action?

I've recently used ACE a lot in applications, and I registered a Ctrl-C handler that called ACE_Reactor::instance()->end_reactor_event_loop();, such that when the user presses Ctrl-C, things get shut down in a nice orderly fashion. They even get a polite message on the screen informing that shutdown operations are pending. :-)

"James Dunne" <jdunne4@bradley.edu> wrote in message news:cu9fgg$28mr$1@digitaldaemon.com...
> Hello,
>
> Can we have a platform-independent way to trap the CTRL-C signal for D
> programs?
> I'm writing a server application that needs to close nicely on a
> CTRL-C under
> Linux.
>
> Also, the static ~this() of modules does not get executed on a CTRL-C,
> and the
> garbage collector is left undestroyed (presumably the memory is freed
> by the OS
> upon program close).
>
> A temporary fix would be to define export functions of the signal()
> routines
> under Linux (which are not in the Phobos linux declaration modules,
> and which
> should be) and call them with extern (C) defined signal-handler
> functions.
>
> Regards,
> James Dunne


February 08, 2005
Something like that would be great in D (or phobos)!  However, it could even be simplified to some special function name like _Dterminate() which would be automatically registered to handle CTRL-C or other kill signals in dmain.d. It'd have to be cross-platform too, of course, and handle Windows signals similarly.

If tempted enough, I might be able to hack out a quick phobos patch for it.

In article <cu9gpv$2cki$1@digitaldaemon.com>, Matthew says...
>
>Would you want to have some kind of Ctrl-C handler registration, whereby an object implementing ICtrlCHandler, or some such, would be passed into a registration function. If the user requires, the implementing instance would have access to state within the (main) thread of execution, such that it could take action?
>
>I've recently used ACE a lot in applications, and I registered a Ctrl-C handler that called ACE_Reactor::instance()->end_reactor_event_loop();, such that when the user presses Ctrl-C, things get shut down in a nice orderly fashion. They even get a polite message on the screen informing that shutdown operations are pending. :-)
>
>"James Dunne" <jdunne4@bradley.edu> wrote in message news:cu9fgg$28mr$1@digitaldaemon.com...
>> Hello,
>>
>> Can we have a platform-independent way to trap the CTRL-C signal for D
>> programs?
>> I'm writing a server application that needs to close nicely on a
>> CTRL-C under
>> Linux.
>>
>> Also, the static ~this() of modules does not get executed on a CTRL-C,
>> and the
>> garbage collector is left undestroyed (presumably the memory is freed
>> by the OS
>> upon program close).
>>
>> A temporary fix would be to define export functions of the signal()
>> routines
>> under Linux (which are not in the Phobos linux declaration modules,
>> and which
>> should be) and call them with extern (C) defined signal-handler
>> functions.
>>
>> Regards,
>> James Dunne
>
>

Regards,
James Dunne
February 08, 2005
James Dunne wrote:
> Hello,
> 
> Can we have a platform-independent way to trap the CTRL-C signal for D programs?
> I'm writing a server application that needs to close nicely on a CTRL-C under
> Linux.
<snip>

As I see it, the simple and logical solution is to have Ctrl+C throw an exception.

But how easy or not would this be to implement?  I'm guessing it would be similar to having an exception for access violation....

Stewart.

-- 
My e-mail is valid but not my primary mailbox.  Please keep replies on the 'group where everyone may benefit.
February 08, 2005
"Stewart Gordon" <smjg_1998@yahoo.com> wrote in message news:cua28q$10ll$1@digitaldaemon.com...
> James Dunne wrote:
>> Hello,
>>
>> Can we have a platform-independent way to trap the CTRL-C signal for
>> D programs?
>> I'm writing a server application that needs to close nicely on a
>> CTRL-C under
>> Linux.
> <snip>
>
> As I see it, the simple and logical solution is to have Ctrl+C throw an exception.

Throw it where, or to whom?

AFAICR, Ctrl-C is a signal on UNIX, and on Win32 the registered callback is invoked asynchronously. Therefore, a thrown exception is not the answer.

> But how easy or not would this be to implement?  I'm guessing it would be similar to having an exception for access violation....
>


February 08, 2005
Matthew wrote:
> "Stewart Gordon" <smjg_1998@yahoo.com> wrote in message news:cua28q$10ll$1@digitaldaemon.com...
<snip>
>> As I see it, the simple and logical solution is to have Ctrl+C throw an exception.
> 
> Throw it where, or to whom?

Where the program counter is at the moment it's pressed.  To whatever catches it - exactly the same as with any exception.

> AFAICR, Ctrl-C is a signal on UNIX, and on Win32 the registered callback is invoked asynchronously. Therefore, a thrown exception is not the answer.
<snip>

Hmm....

Stewart.

-- 
My e-mail is valid but not my primary mailbox.  Please keep replies on the 'group where everyone may benefit.
February 08, 2005
"Stewart Gordon" <smjg_1998@yahoo.com> wrote in message news:cua5g0$18ec$1@digitaldaemon.com...
> Matthew wrote:
>> "Stewart Gordon" <smjg_1998@yahoo.com> wrote in message news:cua28q$10ll$1@digitaldaemon.com...
> <snip>
>>> As I see it, the simple and logical solution is to have Ctrl+C throw an exception.
>>
>> Throw it where, or to whom?
>
> Where the program counter is at the moment it's pressed.  To whatever catches it - exactly the same as with any exception.

Sorry, mate, but that's just crazy. It'd mean that every bit of code, _everywhere_, would have to be written to be mindful of the possibility of catching such an exception, right down to halfway through reading/writing a 64-bit integer.

Not gonna happen.



February 08, 2005
Right, anyway...

It'd be best accomplished with a specialized function as I stated before, that if defined by the user, is the automatically registered callback for the signal or the Windows equivalent of such.

In article <cua74c$1dcm$1@digitaldaemon.com>, Matthew says...
>
>
>"Stewart Gordon" <smjg_1998@yahoo.com> wrote in message news:cua5g0$18ec$1@digitaldaemon.com...
>> Matthew wrote:
>>> "Stewart Gordon" <smjg_1998@yahoo.com> wrote in message news:cua28q$10ll$1@digitaldaemon.com...
>> <snip>
>>>> As I see it, the simple and logical solution is to have Ctrl+C throw an exception.
>>>
>>> Throw it where, or to whom?
>>
>> Where the program counter is at the moment it's pressed.  To whatever catches it - exactly the same as with any exception.
>
>Sorry, mate, but that's just crazy. It'd mean that every bit of code, _everywhere_, would have to be written to be mindful of the possibility of catching such an exception, right down to halfway through reading/writing a 64-bit integer.
>
>Not gonna happen.
>
>
>

Regards,
James Dunne
February 08, 2005
Matthew wrote:
<snip>
>> Where the program counter is at the moment it's pressed. To whatever catches it - exactly the same as with any exception.
> 
> Sorry, mate, but that's just crazy. It'd mean that every bit of code, _everywhere_, would have to be written to be mindful of the possibility of catching such an exception, right down to halfway through reading/writing a 64-bit integer.

So, what is the conventional means of getting round this, be they Unix, MS-DOS or Windows console apps?  Maybe if I knew more about what a signal is....

Stewart.

-- 
My e-mail is valid but not my primary mailbox.  Please keep replies on the 'group where everyone may benefit.
February 08, 2005
Stewart,

A signal, in Linux (or any POSIX compliant OS) at least, is a special message that the OS sends to a process on a special event.  You can think of these signals as sort-of like the Windows message pump idea, if you know how that works.  Basically, the Linux program sets up signal handling functions for the different signals it wants to catch.

For example, the most common signals to trap are SIGTERM and SIGINT.  SIGTERM is a signal sent when the OS needs to TERMinate the process (probably on system shutdown, or via the kill shell command).  The other signal, SIGINT, is the signal sent when the user sends a CTRL-C to the process from the shell.  It is useful to trap this signal in order to shut down programs properly.

As of right now, D offers no protection to CTRL-C signals, or SIGTERM signals in Linux or their equivalents on Windows.  This means that if you CTRL-C or kill a D program, the static module and class destructors will not be called and the GC will not be properly terminated, which is a Bad Thing (TM).

I've written a simple Linux-only signal trapper which will shut down the program correctly and call the static destructors and terminate the GC.  I'm sure there's a way to do this similarly in Windows (probably with the _atexit function, but I'm not sure about that), but in my selfishness, I don't need Windows support for that feature right now, so I didn't bother with it. ;)

If more people are interested, I can hack up a nice phobos patch for this almost-necessary feature!


Here's an example with code:

#import	std.c.stdlib;
#version (linux) import std.c.linux.linux;
#
#// On my machine, this was thrown in at the end of std.c.linux.linuxextern:
#typedef void (*sighandler_t)(int);
#extern (C) sighandler_t signal(int signal, sighandler_t handler);
#
#// These are for control of termination:
#extern (C) void _STD_monitor_staticdtor();
#extern (C) void _STD_critical_term();
#extern (C) void gc_term();
#extern (C) void _moduleDtor();
#
#// Called upon a signal from Linux
#extern (C) void sighandler(int sig) {
#	printf("signal %d caught...\n", sig);
#	terminate();
#}
#
#void terminate() {
#	// Place your own custom shutdown code here!
#
#	// D termination (since we can't really make main() return):
#	_moduleDtor();
#	gc_term();
#	version (linux) {
#		//free(am);
#		_STD_critical_term();
#		_STD_monitor_staticdtor();
#	}
#
#	exit(0);
#}
#
#int main(char[][] args) {
#	// Register the SIGINT signal with the sighandler function call:
#	version (linux) {
#		signal(SIGABRT, &sighandler);
#		signal(SIGTERM, &sighandler);
#		signal(SIGQUIT, &sighandler);
#		signal(SIGINT, &sighandler);
#	}
#
#	try {
#		// Do your main loop code here...
#	} catch (Exception e) {
#		e.print();
#	} finally {
#		// Call your terminate() function to properly terminate the program:
#		terminate();
#	}
#
#	// Don't rely on returning from main if you have custom shutdown code in
terminate():
#	return 0;
#}

In article <cuaq7a$307i$1@digitaldaemon.com>, Stewart Gordon says...
>
>Matthew wrote:
><snip>
>>> Where the program counter is at the moment it's pressed. To whatever catches it - exactly the same as with any exception.
>> 
>> Sorry, mate, but that's just crazy. It'd mean that every bit of code, _everywhere_, would have to be written to be mindful of the possibility of catching such an exception, right down to halfway through reading/writing a 64-bit integer.
>
>So, what is the conventional means of getting round this, be they Unix, MS-DOS or Windows console apps?  Maybe if I knew more about what a signal is....
>
>Stewart.
>
>-- 
>My e-mail is valid but not my primary mailbox.  Please keep replies on the 'group where everyone may benefit.

Regards,
James Dunne
« First   ‹ Prev
1 2
Top | Discussion index | About this forum | D home