1 module mecca.reactor.platform.signals;
2
3 package(mecca.reactor):
4
5 version (linux)
6 import signals = mecca.reactor.platform.linux.signals;
7 else version (Darwin)
8 import signals = mecca.reactor.platform.darwin.signals;
9 else
10 static assert("platform not supported");
11
12 /// ReactorSignal singleton
13 public __gshared signals.ReactorSignal reactorSignal;
14
15 static if (is(signals.signalfd_siginfo))
16 alias signals.signalfd_siginfo signalfd_siginfo;
17
18 unittest {
19 import std.process : environment;
20
21 import mecca.lib.exception : assertGE;
22 import mecca.log : LogToConsole, INFO, WARN;
23 import mecca.reactor : Reactor, theReactor;
24 import mecca.platform.os : OSSignal;
25
26 if( environment.get("DETERMINSTIC_HINT", "0")=="1" ) {
27 WARN!"Skipping signals test due to environment request"();
28 static if( !LogToConsole ) {
29 import std.stdio: stderr;
30 stderr.writeln( "Skipping signals test due to environment request" );
31 }
32 return;
33 }
34
35 Reactor.OpenOptions options;
36
37 // Timing sensitive tests should not suffer GC collection in their middle
38 options.utGcDisabled = true;
39
40 theReactor.setup(options);
41 scope(success) theReactor.teardown();
42
43 uint sigcount;
44
45 void sigHandler(OSSignal) {
46 sigcount++;
47 }
48
49 void fiberCode() {
50 import core.sys.posix.sys.time;
51 import mecca.lib.exception : errnoCall;
52 import mecca.lib.time;
53 import mecca.platform.os : ITIMER_REAL;
54
55 reactorSignal.registerHandler(OSSignal.SIGALRM, &sigHandler);
56
57 itimerval it;
58 it.it_interval.tv_usec = 500; // Wake up every half millisecond. More accurate than our reactor timers ;-)
59 it.it_value = it.it_interval;
60
61 errnoCall!setitimer(ITIMER_REAL, &it, null);
62
63 theReactor.sleep(dur!"msecs"(3));
64
65 // Disarm the timer
66 it.it_value.tv_sec = 0;
67 it.it_value.tv_usec = 0;
68 it.it_interval = it.it_value;
69 errnoCall!setitimer(ITIMER_REAL, &it, null);
70
71 theReactor.stop();
72 }
73
74 theReactor.spawnFiber(&fiberCode);
75
76 theReactor.start();
77
78 INFO!"500µs timer triggered %s time during 3ms sleep"(sigcount);
79 assertGE(sigcount, 5, "Signal count incorrect"); // Will probably be higher
80 }