Skip to content

Commit 30f3c1d

Browse files
committed
first signal support
1 parent c47a91b commit 30f3c1d

File tree

2 files changed

+87
-1
lines changed

2 files changed

+87
-1
lines changed

include/proto_activities.h

Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -416,6 +416,12 @@ namespace proto_activities {
416416
bool did_suspend{};
417417
};
418418

419+
struct Updatable {
420+
virtual ~Updatable() = default;
421+
virtual void update() = 0;
422+
Updatable* next{};
423+
};
424+
419425
struct Enter {
420426
Enter& operator=(const Enter& other) {
421427
thunk = nullptr;
@@ -426,12 +432,20 @@ namespace proto_activities {
426432
thunk();
427433
return *this;
428434
}
435+
void add(Updatable* updatable) {
436+
updatable->next = head;
437+
head = updatable;
438+
}
429439
void invoke() {
440+
for (auto* updatable = head; updatable != nullptr; updatable = updatable->next) {
441+
updatable->update();
442+
}
430443
if (thunk) {
431444
thunk();
432445
}
433446
}
434447
Thunk thunk;
448+
Updatable* head{};
435449
};
436450
}
437451

@@ -487,6 +501,39 @@ namespace proto_activities {
487501

488502
#endif
489503

504+
/* Signals */
505+
506+
#ifdef __cplusplus
507+
namespace proto_activities {
508+
struct BoolSignal final : Updatable {
509+
BoolSignal(Enter& enter) {
510+
enter.add(this);
511+
}
512+
BoolSignal(const BoolSignal&) = delete;
513+
BoolSignal& operator=(const BoolSignal&) {
514+
value_ = false;
515+
return *this;
516+
}
517+
void emit() {
518+
value_ = true;
519+
}
520+
operator bool() const {
521+
return value_;
522+
}
523+
void update() final {
524+
value_ = false;
525+
}
526+
private:
527+
bool value_;
528+
};
529+
}
530+
using pa_signal = proto_activities::BoolSignal;
531+
532+
#define pa_def_signal(nm) pa_signal nm{_pa_enter};
533+
#define pa_emit(sig) sig.emit();
534+
535+
#endif
536+
490537
/* Trigger */
491538

492539
#define pa_init(nm) _pa_reset(&_pa_inst_name(nm));

tests_cpp/tests.cpp

Lines changed: 40 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -640,7 +640,7 @@ pa_activity (TestEvery, pa_ctx(pa_co_res(4); int value; int actual; int expected
640640
} pa_co_end;
641641
} pa_end;
642642

643-
// Test Lifecycle
643+
// Lifecycle Tests
644644

645645
namespace {
646646
bool did_defer = false;
@@ -802,6 +802,44 @@ pa_activity (TestLifecycle, pa_ctx(pa_co_res(2); pa_use(TestLifecycleBody); pa_u
802802
} pa_co_end
803803
} pa_end
804804

805+
// Signal Tests
806+
807+
pa_activity (TestSignalsBodySub, pa_ctx(), pa_signal& s1, pa_signal& s2) {
808+
assert(!s1); assert(!s2);
809+
pa_pause;
810+
811+
assert(!s1); assert(!s2);
812+
pa_emit(s1); pa_emit(s2);
813+
assert(s1); assert(s2);
814+
pa_pause;
815+
816+
assert(!s1); assert(!s2);
817+
pa_pause;
818+
} pa_end
819+
820+
pa_activity (TestSignalsBody, pa_ctx(pa_enter_res; pa_use(TestSignalsBodySub);
821+
pa_def_signal(s1); pa_def_signal(s2))) {
822+
assert(!pa_self.s1); assert(!pa_self.s2);
823+
pa_pause;
824+
825+
assert(!pa_self.s1); assert(!pa_self.s2);
826+
pa_emit(pa_self.s1); pa_emit(pa_self.s2);
827+
assert(pa_self.s1); assert(pa_self.s2);
828+
pa_pause;
829+
830+
assert(!pa_self.s1); assert(!pa_self.s2);
831+
pa_pause;
832+
833+
pa_run(TestSignalsBodySub, pa_self.s1, pa_self.s1);
834+
} pa_end
835+
836+
pa_activity (TestSignals, pa_ctx_tm(pa_use(TestSignalsBody))) {
837+
pa_run (TestSignalsBody);
838+
pa_run (TestSignalsBody); // Test re-invocation
839+
pa_after_abort (2, TestSignalsBody);
840+
pa_run (TestSignalsBody); // Test re-invocation after abort
841+
} pa_end
842+
805843
} // namespace tests
806844

807845
// Test Driver
@@ -822,6 +860,7 @@ int main(int argc, char* argv[]) {
822860
run_test(tests, TestWhenReset);
823861
run_test(tests, TestEvery);
824862
run_test(tests, TestLifecycle);
863+
run_test(tests, TestSignals);
825864

826865
std::cout << "Done" << std::endl;
827866

0 commit comments

Comments
 (0)