Tamer
C++ language extensions for event-driven programming
Loading...
Searching...
No Matches
adapter.hh
Go to the documentation of this file.
1#ifndef TAMER_ADAPTER_HH
2#define TAMER_ADAPTER_HH
3/* Copyright (c) 2007-2015, Eddie Kohler
4 * Copyright (c) 2007, Regents of the University of California
5 *
6 * Permission is hereby granted, free of charge, to any person obtaining a
7 * copy of this software and associated documentation files (the "Software"),
8 * to deal in the Software without restriction, subject to the conditions
9 * listed in the Tamer LICENSE file. These conditions include: you must
10 * preserve this copyright notice, and you cannot mention the copyright
11 * holders in advertising related to the Software without their permission.
12 * The Software is provided WITHOUT ANY WARRANTY, EXPRESS OR IMPLIED. This
13 * notice is a summary of the Tamer LICENSE file; the license in that file is
14 * legally binding.
15 */
16#include <tamer/xadapter.hh>
17namespace tamer {
18
22
32template <typename T0, typename T1, typename T2, typename T3>
35 return e1 += std::move(e2);
36}
37
38#if TAMER_HAVE_PREEVENT
39template <typename R, typename T0>
40inline event<T0> operator+(event<T0> e1, preevent<R, T0>&& e2) {
41 return e1 += std::move(e2);
42}
43
44template <typename R, typename T0>
45inline event<T0> operator+(preevent<R, T0>&& e1, event<T0> e2) {
46 return e2 += std::move(e1);
47}
48#endif
49
59template <typename T0, typename T1, typename T2, typename T3>
62 return e1 += std::move(e2);
63}
64
73template <typename T0, typename T1, typename T2, typename T3>
77 e1 += std::move(e2);
78 return e1 += std::move(e3);
79}
80
81#if TAMER_HAVE_PREEVENT
82template <typename R, typename T0>
83inline event<T0> all(event<T0> e1, preevent<R, T0>&& e2) {
84 return e1 += std::move(e2);
85}
86
87template <typename R, typename T0>
88inline event<T0> all(preevent<R, T0>&& e1, event<T0> e2) {
89 return e2 += std::move(e1);
90}
91#endif
92
103template <size_t I = 0, typename VI = void, typename... TS>
105 tamerpriv::bind_rendezvous<I, VI, TS...>* r =
106 new tamerpriv::bind_rendezvous<I, VI, TS...>(std::move(e), std::move(vi));
107 return r->make_bound();
108}
109
110#if TAMER_HAVE_PREEVENT
111template <typename R, typename T0, typename V0>
112inline event<> bind(preevent<R, T0>&& pe, V0 v0) {
113 return bind(event<T0>(std::move(pe)), std::move(v0));
114}
115#endif
116
126template <typename... TS>
127inline event<TS...> rebind(event<> e) {
128 return tamerpriv::rebinder<TS...>::make(e);
129}
130
131template <typename T0>
132inline event<T0> rebind(event<> e, T0& s0) {
133 return event<T0>(std::move(e), s0);
134}
135
136#if TAMER_HAVE_PREEVENT
137template <typename T0, typename R>
138inline event<T0> rebind(preevent<R>&& pe) {
139 return tamerpriv::rebinder<T0>::make(std::move(pe));
140}
141
142template <typename T0, typename R>
143inline event<T0> rebind(preevent<R>&& pe, T0& s0) {
144 return event<T0>(std::move(pe), s0);
145}
146#endif
147
159template <typename S0, typename T0, typename F>
161 tamerpriv::map_rendezvous<S0, T0, F> *r =
162 new tamerpriv::map_rendezvous<S0, T0, F>(std::move(f), e);
163 event<S0> mapped = TAMER_MAKE_FN_ANNOTATED_EVENT(*r, r->result0());
164 e.at_trigger(mapped.unblocker());
165 return mapped;
166}
167
168#if TAMER_HAVE_PREEVENT
169template <typename S0, typename R, typename T0, typename F>
170event<S0> map(preevent<R, T0>&& pe, F f) {
171 event<T0> e(std::move(pe));
172 tamerpriv::map_rendezvous<S0, T0, F> *r =
173 new tamerpriv::map_rendezvous<S0, T0, F>(std::move(f), e);
174 event<S0> mapped = TAMER_MAKE_FN_ANNOTATED_EVENT(*r, r->result0());
175 e.at_trigger(mapped.unblocker());
176 return mapped;
177}
178#endif
179
180
195template <size_t I = 0, typename V = void, typename... TS>
196inline event<TS...> add_timeout(const timeval& delay, event<TS...> e, V v) {
197 at_delay(delay, tamer::bind<I>(e, std::move(v)));
198 return e;
199}
200
201template <size_t I = 0, typename V = void, typename... TS>
202inline event<TS...> add_timeout(double delay, event<TS...> e, V v) {
203 at_delay(delay, tamer::bind<I>(e, std::move(v)));
204 return e;
205}
206
207template <size_t I = 0, typename V = void, typename... TS>
208inline event<TS...> add_timeout_sec(int delay, event<TS...> e, V v) {
209 at_delay_sec(delay, tamer::bind<I>(e, std::move(v)));
210 return e;
211}
212
213template <size_t I = 0, typename V = void, typename... TS>
214inline event<TS...> add_timeout_msec(int delay, event<TS...> e, V v) {
215 at_delay_msec(delay, tamer::bind<I>(e, std::move(v)));
216 return e;
217}
218
219#if TAMER_HAVE_PREEVENT
220template <typename R, typename T0>
221inline event<T0> add_timeout(const timeval& delay, preevent<R, T0>&& pe, T0 v) {
222 return add_timeout(delay, event<T0>(std::move(pe)), std::move(v));
223}
224
225template <typename R, typename T0>
226inline event<T0> add_timeout(double delay, preevent<R, T0>&& pe, T0 v) {
227 return add_timeout(delay, event<T0>(std::move(pe)), std::move(v));
228}
229
230template <typename R, typename T0>
231inline event<T0> add_timeout_sec(int delay, preevent<R, T0>&& pe, T0 v) {
232 return add_timeout_sec(delay, event<T0>(std::move(pe)), std::move(v));
233}
234
235template <typename R, typename T0>
236inline event<T0> add_timeout_msec(int delay, preevent<R, T0>&& pe, T0 v) {
237 return add_timeout_msec(delay, event<T0>(std::move(pe)), std::move(v));
238}
239#endif
240
254template <typename... TS>
255inline event<TS...> add_timeout(const timeval& delay, event<TS...> e) {
256 at_delay(delay, e.unblocker());
257 return e;
258}
259
260template <typename... TS>
261inline event<TS...> add_timeout(double delay, event<TS...> e) {
262 at_delay(delay, e.unblocker());
263 return e;
264}
265
266template <typename... TS>
267inline event<TS...> add_timeout_sec(int delay, event<TS...> e) {
268 at_delay_sec(delay, e.unblocker());
269 return e;
270}
271
272template <typename... TS>
273inline event<TS...> add_timeout_msec(int delay, event<TS...> e) {
274 at_delay_msec(delay, e.unblocker());
275 return e;
276}
277
278#if TAMER_HAVE_PREEVENT
279template <typename T0, typename R>
280inline event<T0> add_timeout(const timeval& delay, preevent<R, T0>&& pe) {
281 return add_timeout(delay, event<T0>(std::move(pe)));
282}
283
284template <typename T0, typename R>
285inline event<T0> add_timeout(double delay, preevent<R, T0>&& pe) {
286 return add_timeout(delay, event<T0>(std::move(pe)));
287}
288
289template <typename T0, typename R>
290inline event<T0> add_timeout_sec(int delay, preevent<R, T0>&& pe) {
291 return add_timeout_sec(delay, event<T0>(std::move(pe)));
292}
293
294template <typename T0, typename R>
295inline event<T0> add_timeout_msec(int delay, preevent<R, T0>&& pe) {
296 return add_timeout_msec(delay, event<T0>(std::move(pe)));
297}
298#endif
299
300
310template <typename T0>
311inline event<T0> add_signal(int signo, event<T0> e, T0 v) {
312 at_signal(signo, tamer::bind(e, std::move(v)));
313 return e;
314}
315
316#if TAMER_HAVE_PREEVENT
317template <typename R, typename T0>
318inline event<T0> add_signal(int signo, preevent<R, T0>&& pe, T0 v) {
319 return add_signal(signo, event<T0>(std::move(pe)), std::move(v));
320}
321#endif
322
334template <typename T0, typename SigInputIterator>
335inline event<T0> add_signal(SigInputIterator first, SigInputIterator last, event<T0> e, T0 v) {
336 event<> x = tamer::bind(e, std::move(v));
337 for (; first != last; ++first) {
338 at_signal(*first, x);
339 }
340 return e;
341}
342
343#if TAMER_HAVE_PREEVENT
344template <typename R, typename T0, typename SigInputIterator>
345inline event<T0> add_signal(SigInputIterator first, SigInputIterator last, preevent<R, T0>&& pe, T0 v) {
346 return add_signal(first, last, event<T0>(std::move(pe)), std::move(v));
347}
348#endif
349
358template <typename T0>
359inline event<T0> add_signal(int signo, event<T0> e) {
360 at_signal(signo, e.unblocker());
361 return e;
362}
363
364#if TAMER_HAVE_PREEVENT
365template <typename T0, typename R>
366inline event<T0> add_signal(int signo, preevent<R, T0>&& pe) {
367 return add_signal(signo, event<T0>(std::move(pe)));
368}
369#endif
370
381template <typename T0, typename SigInputIterator>
382inline event<T0> add_signal(SigInputIterator first, SigInputIterator last, event<T0> e) {
383 for (; first != last; ++first) {
384 at_signal(*first, e);
385 }
386 return e;
387}
388
389#if TAMER_HAVE_PREEVENT
390template <typename T0, typename R, typename SigInputIterator>
391inline event<T0> add_signal(SigInputIterator first, SigInputIterator last, preevent<R, T0>&& pe) {
392 return add_signal(first, last, event<T0>(std::move(pe)));
393}
394#endif
395
396
410template <typename T0, typename T1, typename T2, typename T3>
412 at_delay(delay, e.unblocker());
413 return e;
414}
415
416template <typename T0, typename T1, typename T2, typename T3>
417inline event<T0, T1, T2, T3> with_timeout(double delay, event<T0, T1, T2, T3> e) {
418 at_delay(delay, e.unblocker());
419 return e;
420}
421
422template <typename T0, typename T1, typename T2, typename T3>
423inline event<T0, T1, T2, T3> with_timeout_sec(int delay, event<T0, T1, T2, T3> e) {
424 at_delay_sec(delay, e.unblocker());
425 return e;
426}
427
428template <typename T0, typename T1, typename T2, typename T3>
429inline event<T0, T1, T2, T3> with_timeout_msec(int delay, event<T0, T1, T2, T3> e) {
430 at_delay_msec(delay, e.unblocker());
431 return e;
432}
433
434#if TAMER_HAVE_PREEVENT
435template <typename R, typename T0>
436inline event<T0> with_timeout(const timeval& delay, preevent<R, T0>&& pe) {
437 return with_timeout(delay, event<T0>(std::move(pe)));
438}
439
440template <typename R, typename T0>
441inline event<T0> with_timeout(double delay, preevent<R, T0>&& pe) {
442 return with_timeout(delay, event<T0>(std::move(pe)));
443}
444
445template <typename R, typename T0>
446inline event<T0> with_timeout_sec(int delay, preevent<R, T0>&& pe) {
447 return with_timeout_sec(delay, event<T0>(std::move(pe)));
448}
449
450template <typename R, typename T0>
451inline event<T0> with_timeout_msec(int delay, preevent<R, T0>&& pe) {
452 return with_timeout_msec(delay, event<T0>(std::move(pe)));
453}
454#endif
455
464template <typename T0, typename T1, typename T2, typename T3>
466 at_signal(signo, e.unblocker());
467 return e;
468}
469
470#if TAMER_HAVE_PREEVENT
471template <typename R, typename T0>
472inline event<T0> with_signal(int signo, preevent<R, T0>&& pe) {
473 return with_signal(signo, event<T0>(std::move(pe)));
474}
475#endif
476
487template <typename T0, typename T1, typename T2, typename T3, typename SigInputIterator>
488inline event<T0, T1, T2, T3> with_signal(SigInputIterator first, SigInputIterator last, event<T0, T1, T2, T3> e) {
489 event<> x = e.unblocker();
490 for (; first != last; ++first) {
491 at_signal(*first, x);
492 }
493 return e;
494}
495
496#if TAMER_HAVE_PREEVENT
497template <typename R, typename T0, typename SigInputIterator>
498inline event<T0> with_signal(SigInputIterator first, SigInputIterator last, preevent<R, T0>&& pe) {
499 return with_signal(first, last, event<T0>(std::move(pe)));
500}
501#endif
502
503
519template <typename T0, typename T1, typename T2, typename T3>
520inline event<T0, T1, T2, T3> with_timeout(const timeval &delay, event<T0, T1, T2, T3> e, int &result) {
521 at_delay(delay, tamerpriv::with_helper(e, &result, outcome::timeout));
522 return e;
523}
524
525template <typename T0, typename T1, typename T2, typename T3>
526inline event<T0, T1, T2, T3> with_timeout(double delay, event<T0, T1, T2, T3> e, int &result) {
527 at_delay(delay, tamerpriv::with_helper(e, &result, outcome::timeout));
528 return e;
529}
530
531template <typename T0, typename T1, typename T2, typename T3>
532inline event<T0, T1, T2, T3> with_timeout_sec(int delay, event<T0, T1, T2, T3> e, int &result) {
533 at_delay_sec(delay, tamerpriv::with_helper(e, &result, outcome::timeout));
534 return e;
535}
536
537template <typename T0, typename T1, typename T2, typename T3>
538inline event<T0, T1, T2, T3> with_timeout_msec(int delay, event<T0, T1, T2, T3> e, int &result) {
539 at_delay_msec(delay, tamerpriv::with_helper(e, &result, outcome::timeout));
540 return e;
541}
542
543#if TAMER_HAVE_PREEVENT
544template <typename R, typename T0>
545inline event<T0> with_timeout(const timeval& delay, preevent<R, T0>&& pe, int& result) {
546 return with_timeout(delay, event<T0>(std::move(pe)), result);
547}
548
549template <typename R, typename T0>
550inline event<T0> with_timeout(double delay, preevent<R, T0>&& pe, int& result) {
551 return with_timeout(delay, event<T0>(std::move(pe)), result);
552}
553
554template <typename R, typename T0>
555inline event<T0> with_timeout_sec(int delay, preevent<R, T0>&& pe, int& result) {
556 return with_timeout_sec(delay, event<T0>(std::move(pe)), result);
557}
558
559template <typename R, typename T0>
560inline event<T0> with_timeout_msec(int delay, preevent<R, T0>&& pe, int& result) {
561 return with_timeout_msec(delay, event<T0>(std::move(pe)), result);
562}
563#endif
564
576template <typename T0, typename T1, typename T2, typename T3>
577inline event<T0, T1, T2, T3> with_signal(int signo, event<T0, T1, T2, T3> e, int &result) {
578 at_signal(signo, tamerpriv::with_helper(e, &result, outcome::signal));
579 return e;
580}
581
582#if TAMER_HAVE_PREEVENT
583template <typename R, typename T0>
584inline event<T0> with_signal(int signo, preevent<R, T0>&& pe, int& result) {
585 return with_signal(signo, event<T0>(std::move(pe)), result);
586}
587#endif
588
601template <typename T0, typename T1, typename T2, typename T3, typename SigInputIterator>
602inline event<T0, T1, T2, T3> with_signal(SigInputIterator first, SigInputIterator last, event<T0, T1, T2, T3> e, int &result) {
603 event<> x = tamerpriv::with_helper(e, &result, outcome::signal);
604 for (; first != last; ++first) {
605 at_signal(*first, x);
606 }
607 return e;
608}
609
610#if TAMER_HAVE_PREEVENT
611template <typename R, typename T0, typename SigInputIterator>
612inline event<T0> with_signal(SigInputIterator first, SigInputIterator last, preevent<R, T0>&& pe, int& result) {
613 return with_signal(first, last, event<T0>(std::move(pe)), result);
614}
615#endif
616
617
626template <typename F>
627inline event<> fun_event(F f) {
628 tamerpriv::function_rendezvous<F> *innerr =
629 new tamerpriv::function_rendezvous<F>(std::move(f));
630 return tamer::make_event(*innerr);
631}
632
642template <typename F, typename A>
643inline event<> fun_event(F f, A arg) {
644 tamerpriv::function_rendezvous<F, A> *innerr =
645 new tamerpriv::function_rendezvous<F, A>(std::move(f),
646 std::move(arg));
647 return TAMER_MAKE_FN_ANNOTATED_EVENT(*innerr);
648}
649
660template <typename F, typename A1, typename A2>
661inline event<> fun_event(F f, A1 arg1, A2 arg2) {
662 tamerpriv::function_rendezvous<F, A1, A2> *innerr =
663 new tamerpriv::function_rendezvous<F, A1, A2>(std::move(f),
664 std::move(arg1),
665 std::move(arg2));
666 return TAMER_MAKE_FN_ANNOTATED_EVENT(*innerr);
667}
668
669
670template <typename C>
671inline event<typename C::value_type> push_back_event(C& container) {
672 tamerpriv::push_back_rendezvous<C>* r =
673 new tamerpriv::push_back_rendezvous<C>(container);
674 return TAMER_MAKE_FN_ANNOTATED_EVENT(*r, r->slot());
675}
676
677template <typename It>
678inline event<typename std::iterator_traits<It>::value_type> output_event(It& iterator) {
679 tamerpriv::output_rendezvous<It>* r =
680 new tamerpriv::output_rendezvous<It>(iterator);
681 return TAMER_MAKE_FN_ANNOTATED_EVENT(*r, r->slot());
682}
683
684} /* namespace tamer */
685#endif /* TAMER_ADAPTER_HH */
A future occurrence.
Definition event.hh:116
void at_trigger(const event<> &e)
Register a trigger notifier.
Definition event.hh:785
event unblocker() const noexcept
Return a no-result event for the same occurrence as e.
Definition event.hh:805
event< T0, T1, T2, T3 > make_event(one_argument_rendezvous_tag< R > &r, const I &eid, T0 &x0, T1 &x1, T2 &x2, T3 &x3)
Construct a four-result event on rendezvous r with ID eid.
Definition event.hh:1115
Namespace containing public Tamer classes and functions for the Tamer core.
Definition adapter.hh:17
event bind(event< TS... > e, VI vi)
Create bound event for e with vi.
Definition adapter.hh:104
event< T0, T1, T2, T3 > with_timeout(const timeval &delay, event< T0, T1, T2, T3 > e)
Add silent timeout to an event.
Definition adapter.hh:411
event< TS... > rebind(event<> e)
Create bound event for e.
Definition adapter.hh:127
void at_signal(int signo, event<> e)
Register event for signal occurrence.
Definition driver.hh:239
event< T0, T1, T2, T3 > all(event< T0, T1, T2, T3 > e1, event< T0, T1, T2, T3 > e2)
Create event that triggers e1 and e2 when triggered.
Definition adapter.hh:60
event< T0, T1, T2, T3 > operator+(event< T0, T1, T2, T3 > e1, event< T0, T1, T2, T3 > e2)
Create event that triggers e1 and e2 when triggered.
Definition adapter.hh:33
void at_delay_sec(int delay, event<> e, bool bg=false)
Register event for a given delay.
Definition driver.hh:204
event< T0 > add_signal(int signo, event< T0 > e, T0 v)
Add signal interruption to an event.
Definition adapter.hh:311
void at_delay_msec(int delay, event<> e, bool bg=false)
Register event for a given delay.
Definition driver.hh:216
void at_delay(const timeval &delay, event<> e, bool bg=false)
Register event for a given delay.
Definition driver.hh:180
event< T0, T1, T2, T3 > with_signal(int signo, event< T0, T1, T2, T3 > e)
Add silent signal interruption to an event.
Definition adapter.hh:465
event fun_event(F f)
Create event that calls a function when triggered.
Definition adapter.hh:627
event< S0 > map(event< T0 > e, F f)
Create an event that triggers another event with a mapped value.
Definition adapter.hh:160
event< TS... > add_timeout(const timeval &delay, event< TS... > e, V v)
Add timeout to an event.
Definition adapter.hh:196