diff --git a/cmake/modules/ExternalDependenciesVersions.cmake b/cmake/modules/ExternalDependenciesVersions.cmake index 8ccd88e37..e36fd7aea 100644 --- a/cmake/modules/ExternalDependenciesVersions.cmake +++ b/cmake/modules/ExternalDependenciesVersions.cmake @@ -6,5 +6,5 @@ set(TTG_TRACKED_BOOST_VERSION 1.66) set(TTG_TRACKED_CATCH2_VERSION 2.13.1) set(TTG_TRACKED_CEREAL_VERSION 1.3.0) set(TTG_TRACKED_MADNESS_TAG 31b2470ca722a6a2d84d4de08d32fb72ae8fdeda) -set(TTG_TRACKED_PARSEC_TAG 6a5a986d6ec1f9cace09f3ad475c553632077a24) +set(TTG_TRACKED_PARSEC_TAG 8690b1eb6080500af1ad32ffcd4b95aa38f65c22) set(TTG_TRACKED_BTAS_TAG d73153ad9bc41a177e441ef04eceff7fab0c766d) diff --git a/cmake/modules/FindOrFetchPARSEC.cmake b/cmake/modules/FindOrFetchPARSEC.cmake index 82d6ac0d9..8df410039 100644 --- a/cmake/modules/FindOrFetchPARSEC.cmake +++ b/cmake/modules/FindOrFetchPARSEC.cmake @@ -16,7 +16,7 @@ if (NOT TARGET PaRSEC::parsec) FetchContent_Declare( PARSEC - GIT_REPOSITORY https://github.com/ICLDisco/parsec.git + GIT_REPOSITORY https://github.com/devreal/parsec-1.git GIT_TAG ${TTG_TRACKED_PARSEC_TAG} ) FetchContent_MakeAvailable(PARSEC) diff --git a/tests/unit/tt.cc b/tests/unit/tt.cc index 04b6719cd..2ee7d7612 100644 --- a/tests/unit/tt.cc +++ b/tests/unit/tt.cc @@ -438,7 +438,7 @@ TEST_CASE("TemplateTask", "[core]") { } } -//#if 0 +#if 0 SECTION("split_construction") { ttg::Edge a2b, b2a; /* construct without edges */ @@ -455,5 +455,17 @@ TEST_CASE("TemplateTask", "[core]") { bool is_executable = ttg::make_graph_executable(tta); CHECK(is_executable); } -//#endif // 0 +#endif // 0 + + + SECTION("make_connect") { + ttg::Edge a2b, b2a; + /* construct without edges */ + auto tta = ttg::make_tt([](int key, float value){}); + auto ttb = ttg::make_tt([](int key, float value){}); + ttg::connect<0, 0>(ttb, tta); // B -> A + ttg::connect<0, 0>(tta, ttb); // A -> B + bool is_executable = ttg::make_graph_executable(tta); + CHECK(is_executable); + } } diff --git a/ttg/ttg/func.h b/ttg/ttg/func.h index e383ebbc8..cbcfe386f 100644 --- a/ttg/ttg/func.h +++ b/ttg/ttg/func.h @@ -98,11 +98,25 @@ namespace ttg { inline void connect(ttg::TerminalBase *out, ttg::TerminalBase *in) { out->connect(in); } /// \brief Connect producer output terminal outindex to consumer input terminal inindex (via unique or otherwise - /// wrapped pointers to TTs) \tparam outindex The index of the output terminal on the producer. \tparam inindex The - /// index of the input terminal on the consumer. \param p The producer TT \param c The consumer TT + /// wrapped pointers to TTs) + /// \tparam outindex The index of the output terminal on the producer. + /// \tparam inindex The index of the input terminal on the consumer. + /// \param p The producer TT + /// \param c The consumer TT template inline void connect(producer_tt_ptr &p, successor_tt_ptr &s) { - connect(p->template out(), s->template in()); + // check whether the output terminal is available at compile time + using producer_type = typename std::pointer_traits::element_type; + if constexpr (std::tuple_size_v == 0) { + // need to make sure the output terminal is available + using successor_type = typename std::pointer_traits::element_type; + using input_terminal_type = std::tuple_element_t; + using key_type = typename input_terminal_type::key_type; + using value_type = typename input_terminal_type::value_type; + connect(p->template out(), s->template in()); + } else { + connect(p->template out(), s->template in()); + } } /// \brief Connect producer output terminal outindex to consumer input terminal inindex (via bare pointers to TTs) diff --git a/ttg/ttg/parsec/ttg.h b/ttg/ttg/parsec/ttg.h index 42b60477a..c7ae54dba 100644 --- a/ttg/ttg/parsec/ttg.h +++ b/ttg/ttg/parsec/ttg.h @@ -2791,7 +2791,7 @@ namespace ttg_parsec { , priomap(decltype(keymap)(std::forward(priomap_))) , static_stream_goal() { // Cannot call these in base constructor since terminals not yet constructed - if (innames.size() != numinedges) throw std::logic_error("ttg_parsec::TT: #input names != #input terminals"); + //if (innames.size() != numinedges) throw std::logic_error("ttg_parsec::TT: #input names != #input terminals"); if (outnames.size() != numouts) throw std::logic_error("ttg_parsec::TT: #output names != #output terminals"); auto &world_impl = world.impl(); @@ -3021,10 +3021,48 @@ namespace ttg_parsec { // cannot be copied, moved or assigned. // Only valid if terminals are provided during construction. template - std::tuple_element_t *out() { + auto *out() { + static_assert(std::tuple_size_v > 0, + "TT::out() only available for statically known output terminals. " + "Use TT::out() instead!"); return &std::get(output_terminals); } + template + auto *out(const std::string name = {}) { + using terminal_type = typename ttg::Out; + if constexpr (std::tuple_size_v == 0) { + auto& outputs = this->get_outputs(); + terminal_type *terminal; + if (outputs.size() <= i || nullptr == outputs[i]) { + // create a new terminal + std::string auto_name; + if (name.empty()) { + auto_name = "DynamicOut" + std::to_string(i); + } + terminal = new terminal_type(); + dynamic_outterms.push_back(std::unique_ptr(terminal)); + register_terminal(*terminal, name.empty() ? auto_name : name, &ttT::set_output_dynamic); + } else { +#ifndef NDEBUG + // use dyanmic cast in debug builds + terminal = dynamic_cast(outputs[i]); + if (nullptr == terminal) { + throw std::runtime_error(std::string("TT::out(): failed to cast existing output terminal ") + std::to_string(i)); + } +#else + terminal = static_cast(outputs[i]); +#endif // NDEBUG + } + return terminal; + } else { + static_assert(std::is_same_v>, + "TT::out() key/value types do not match compile-time output terminals."); + return &std::get(output_terminals); + } + } + + // Manual injection of a task with all input arguments specified as a tuple template std::enable_if_t && !ttg::meta::is_empty_tuple_v, void> invoke(