From 9e2e1e60d51f8753e48c660993899766b850290d Mon Sep 17 00:00:00 2001 From: Tarun Prabhu Date: Wed, 16 Aug 2023 16:13:34 -0600 Subject: [PATCH 01/15] WIP: Add (de)serialization support for data structures in lib/pcg. - Have types use the visitable interface. - Add stubs for functions/methods that have a declaration but not definition. These should fail with a "not implemented" message. - Some code clean up. Remove unnecessary constructors. Delete code that has been commented out. Remove files that don't contain any non-header files that do not contain any executable code. --- .../include/op-attrs/parallel_tensor_dims.h | 9 ++- .../include/op-attrs/parallel_tensor_shape.h | 6 +- lib/op-attrs/include/op-attrs/tensor_shape.h | 17 ++--- lib/pcg/CMakeLists.txt | 1 + .../include/pcg/computation_graph_builder.h | 16 ++--- lib/pcg/include/pcg/file_format/v1/graphs.h | 15 +++- .../include/pcg/file_format/v1/initializer.h | 3 + .../pcg/file_format/v1/parallel_tensor.h | 17 ++++- .../include/pcg/file_format/v1/param_sync.h | 3 + lib/pcg/include/pcg/file_format/v1/tensor.h | 6 +- lib/pcg/include/pcg/file_format/v1/v1.h | 13 +++- lib/pcg/include/pcg/layer.h | 12 ++-- lib/pcg/include/pcg/operator.h | 17 ++--- lib/pcg/include/pcg/parallel_tensor.h | 10 ++- lib/pcg/include/pcg/tensor.h | 11 +-- lib/pcg/src/file_format/v1/graphs.cc | 4 ++ lib/pcg/src/file_format/v1/tensor.cc | 16 +++++ lib/pcg/src/layer.cc | 9 --- lib/pcg/test/CMakeLists.txt | 28 ++++++++ lib/pcg/test/doctest.h | 70 +++++++++++++++++++ lib/pcg/test/main.cc | 2 + lib/pcg/test/test_tensor.cc | 14 ++++ lib/utils/include/utils/graph/algorithms.h | 2 + lib/utils/include/utils/graph/cow_ptr_t.h | 4 +- lib/utils/include/utils/graph/multidigraph.h | 1 + .../utils/graph/multidigraph_interfaces.h | 1 + lib/utils/src/graph/adjacency_digraph.cc | 4 ++ lib/utils/src/graph/adjacency_multidigraph.cc | 5 ++ lib/utils/src/graph/algorithms.cc | 17 +++++ lib/utils/src/graph/digraph.cc | 17 +++++ 30 files changed, 266 insertions(+), 84 deletions(-) create mode 100644 lib/pcg/src/file_format/v1/tensor.cc delete mode 100644 lib/pcg/src/layer.cc create mode 100644 lib/pcg/test/CMakeLists.txt create mode 100644 lib/pcg/test/doctest.h create mode 100644 lib/pcg/test/main.cc create mode 100644 lib/pcg/test/test_tensor.cc diff --git a/lib/op-attrs/include/op-attrs/parallel_tensor_dims.h b/lib/op-attrs/include/op-attrs/parallel_tensor_dims.h index d38ba75232..d7b25aecd5 100644 --- a/lib/op-attrs/include/op-attrs/parallel_tensor_dims.h +++ b/lib/op-attrs/include/op-attrs/parallel_tensor_dims.h @@ -6,7 +6,7 @@ namespace FlexFlow { -struct ParallelTensorDims : public use_visitable_cmp { +struct ParallelTensorDims { explicit ParallelTensorDims(TensorDims const &); size_t get_volume() const; @@ -38,16 +38,15 @@ struct ParallelTensorDims : public use_visitable_cmp { const_reverse_iterator crend() const; public: - FFOrdered data; + req> data; }; +FF_VISITABLE_STRUCT_NONSTANDARD_CONSTRUCTION(ParallelTensorDims, data); + bool is_valid(ParallelTensorDims const &); TensorDims get_piece_dims(ParallelTensorDims const &); TensorDims get_tensor_dims_unsafe(ParallelTensorDims const &); } // namespace FlexFlow -VISITABLE_STRUCT(::FlexFlow::ParallelTensorDims, data); -MAKE_VISIT_HASHABLE(::FlexFlow::ParallelTensorDims); - #endif diff --git a/lib/op-attrs/include/op-attrs/parallel_tensor_shape.h b/lib/op-attrs/include/op-attrs/parallel_tensor_shape.h index fd560352bb..7ebfa947de 100644 --- a/lib/op-attrs/include/op-attrs/parallel_tensor_shape.h +++ b/lib/op-attrs/include/op-attrs/parallel_tensor_shape.h @@ -16,7 +16,7 @@ namespace FlexFlow { /** * @brief Represent the shape of a ParallelTensor. */ -struct ParallelTensorShape : public use_visitable_cmp { +struct ParallelTensorShape { ParallelTensorShape() = delete; template @@ -36,6 +36,7 @@ struct ParallelTensorShape : public use_visitable_cmp { ParallelTensorDims dims; DataType data_type; }; +FF_VISITABLE_STRUCT(ParallelTensorShape, dims, data_type); TensorShape get_piece_shape(ParallelTensorShape const &); int get_num_replica_dims(ParallelTensorShape const &); @@ -49,7 +50,4 @@ std::vector } // namespace FlexFlow -VISITABLE_STRUCT(::FlexFlow::ParallelTensorShape, data_type, dims); -MAKE_VISIT_HASHABLE(::FlexFlow::ParallelTensorShape); - #endif diff --git a/lib/op-attrs/include/op-attrs/tensor_shape.h b/lib/op-attrs/include/op-attrs/tensor_shape.h index fa34860817..2c0cd562d2 100644 --- a/lib/op-attrs/include/op-attrs/tensor_shape.h +++ b/lib/op-attrs/include/op-attrs/tensor_shape.h @@ -11,24 +11,17 @@ namespace FlexFlow { using TensorDims = FFOrdered; -struct TensorShape : public use_visitable_cmp { - TensorShape() = delete; - - template - TensorShape(Dims const &dims, DataType data_type) - : dims(dims), data_type(data_type) {} - +struct TensorShape { size_t at(ff_dim_t) const; size_t operator[](ff_dim_t) const; public: - TensorDims dims; - DataType data_type; + req dims; + req data_type; }; -} // namespace FlexFlow +FF_VISITABLE_STRUCT(TensorShape, dims, data_type); -VISITABLE_STRUCT(::FlexFlow::TensorShape, dims, data_type); -MAKE_VISIT_HASHABLE(::FlexFlow::TensorShape); +} // namespace FlexFlow #endif diff --git a/lib/pcg/CMakeLists.txt b/lib/pcg/CMakeLists.txt index 81009b0f1f..e1875ca694 100644 --- a/lib/pcg/CMakeLists.txt +++ b/lib/pcg/CMakeLists.txt @@ -13,3 +13,4 @@ ff_add_library( ) add_subdirectory(ffi) +add_subdirectory(test) diff --git a/lib/pcg/include/pcg/computation_graph_builder.h b/lib/pcg/include/pcg/computation_graph_builder.h index 7f01439712..2722214251 100644 --- a/lib/pcg/include/pcg/computation_graph_builder.h +++ b/lib/pcg/include/pcg/computation_graph_builder.h @@ -5,11 +5,8 @@ namespace FlexFlow { -struct ComputationGraphBuilder - : public use_visitable_cmp { +struct ComputationGraphBuilder { public: - ComputationGraphBuilder(); - // C++ APIs for constructing models // Add an exp layer Tensor exp(Tensor const &, optional const &name = nullopt); @@ -280,16 +277,11 @@ struct ComputationGraphBuilder optional const &name = nullopt); public: - ComputationGraph computation_graph; + req computation_graph; }; -} // namespace FlexFlow - -VISITABLE_STRUCT(::FlexFlow::ComputationGraphBuilder, computation_graph); +FF_VISITABLE_STRUCT(ComputationGraphBuilder, computation_graph); -namespace FlexFlow { -static_assert( - is_well_behaved_value_type_no_hash::value, ""); -} +} // namespace FlexFlow #endif diff --git a/lib/pcg/include/pcg/file_format/v1/graphs.h b/lib/pcg/include/pcg/file_format/v1/graphs.h index 71a8adb344..09d6f1ad0e 100644 --- a/lib/pcg/include/pcg/file_format/v1/graphs.h +++ b/lib/pcg/include/pcg/file_format/v1/graphs.h @@ -16,6 +16,7 @@ struct V1GraphOutput { req srcNode; req srcIdx; }; + FF_VISITABLE_STRUCT(V1GraphOutput, srcNode, srcIdx); CHECK_IS_JSONABLE(V1GraphOutput); @@ -25,6 +26,7 @@ struct V1GraphEdge { req dstNode; req dstIdx; }; + FF_VISITABLE_STRUCT(V1GraphEdge, srcNode, srcIdx, dstNode, dstIdx); CHECK_IS_JSONABLE(V1GraphEdge); @@ -33,6 +35,7 @@ struct V1MultiDiGraph { req> ports; req> edges; }; + FF_VISITABLE_STRUCT(V1MultiDiGraph, nodes, ports, edges); CHECK_IS_JSONABLE(V1MultiDiGraph); V1MultiDiGraph to_v1(MultiDiGraphView const &); @@ -55,6 +58,7 @@ struct V1Layer { V1CompGraphOperatorAttrs attrs; req> name; }; + FF_VISITABLE_STRUCT(V1Layer, attrs, name); V1Layer to_v1(Layer const &); @@ -64,8 +68,17 @@ FF_VISITABLE_STRUCT( CHECK_IS_JSONABLE(V1ComputationGraph); V1ComputationGraph to_v1(ComputationGraph const &); +struct V1Operator { + V1PCGOperatorAttrs attrs; + req> name; +}; + +FF_VISITABLE_STRUCT(V1Operator, attrs, name); +V1Operator to_v1(Operator const &); + using V1ParallelComputationGraph = - V1JsonableGraph; + V1JsonableGraph; + FF_VISITABLE_STRUCT( V1ParallelComputationGraph, node_labels, outputs, output_labels, graph); CHECK_IS_JSONABLE(V1ParallelComputationGraph); diff --git a/lib/pcg/include/pcg/file_format/v1/initializer.h b/lib/pcg/include/pcg/file_format/v1/initializer.h index 24f0320bd9..17272218ae 100644 --- a/lib/pcg/include/pcg/file_format/v1/initializer.h +++ b/lib/pcg/include/pcg/file_format/v1/initializer.h @@ -2,6 +2,7 @@ #define _FLEXFLOW_PCG_INCLUDE_PCG_FILE_FORMAT_V1_INITIALIZER_H #include "data_type.h" +#include "pcg/initializer.h" #include "utils/json.h" #include "utils/required.h" #include "utils/variant.h" @@ -43,6 +44,8 @@ using V1Initializer = variant; +V1Initializer to_v1(Initializer const &); + } // namespace FlexFlow namespace FlexFlow { diff --git a/lib/pcg/include/pcg/file_format/v1/parallel_tensor.h b/lib/pcg/include/pcg/file_format/v1/parallel_tensor.h index 1ea4cd04de..d8a2a00ee4 100644 --- a/lib/pcg/include/pcg/file_format/v1/parallel_tensor.h +++ b/lib/pcg/include/pcg/file_format/v1/parallel_tensor.h @@ -4,6 +4,7 @@ #include "data_type.h" #include "initializer.h" #include "param_sync.h" +#include "pcg/parallel_tensor.h" #include "utils/json.h" #include "utils/variant.h" #include "utils/visitable.h" @@ -15,22 +16,32 @@ struct V1ParallelDim { req degree; req is_replica_dim; }; + FF_VISITABLE_STRUCT(V1ParallelDim, size, degree, is_replica_dim); +CHECK_IS_JSONABLE(V1ParallelDim); +V1ParallelDim to_v1(ParallelDim const &); struct V1ParallelTensorShape { req> dims; req data_type; }; + FF_VISITABLE_STRUCT(V1ParallelTensorShape, dims, data_type); +CHECK_IS_JSONABLE(V1ParallelTensorShape); +V1ParallelTensorShape to_v1(ParallelTensorShape const &); struct V1ParallelTensor { V1ParallelTensorShape shape; - req> sync_type; + req create_gradients; req> initializer; - req create_grad; + req> sync_type; + req> name; }; + FF_VISITABLE_STRUCT( - V1ParallelTensor, shape, sync_type, initializer, create_grad); + V1ParallelTensor, shape, create_gradients, initializer, sync_type, name); +CHECK_IS_JSONABLE(V1ParallelTensor); +V1ParallelTensor to_v1(ParallelTensor const &); } // namespace FlexFlow diff --git a/lib/pcg/include/pcg/file_format/v1/param_sync.h b/lib/pcg/include/pcg/file_format/v1/param_sync.h index 32769a8d20..286abd9c11 100644 --- a/lib/pcg/include/pcg/file_format/v1/param_sync.h +++ b/lib/pcg/include/pcg/file_format/v1/param_sync.h @@ -1,12 +1,15 @@ #ifndef _FLEXFLOW_PCG_FILE_FORMAT_V1_PARAM_SYNC_H #define _FLEXFLOW_PCG_FILE_FORMAT_V1_PARAM_SYNC_H +#include "op-attrs/param_sync.h" #include "utils/json.h" namespace FlexFlow { enum class V1ParamSync { PARAM_SERVER, NCCL }; +V1ParamSync to_v1(ParamSync const &); + NLOHMANN_JSON_SERIALIZE_ENUM(V1ParamSync, {{V1ParamSync::PARAM_SERVER, "PARAM_SERVER"}, {V1ParamSync::NCCL, "NCCL"}}); diff --git a/lib/pcg/include/pcg/file_format/v1/tensor.h b/lib/pcg/include/pcg/file_format/v1/tensor.h index e1f6828186..7aaf0012de 100644 --- a/lib/pcg/include/pcg/file_format/v1/tensor.h +++ b/lib/pcg/include/pcg/file_format/v1/tensor.h @@ -17,18 +17,20 @@ struct V1TensorShape { }; FF_VISITABLE_STRUCT(V1TensorShape, dims, data_type); CHECK_IS_JSONABLE(V1TensorShape); + V1TensorShape to_v1(TensorShape const &); struct V1Tensor { V1TensorShape shape; - req> initializer; req create_gradients; + req> initializer; req> sync_type; req> name; }; FF_VISITABLE_STRUCT( - V1Tensor, shape, initializer, create_gradients, sync_type, name); + V1Tensor, shape, create_gradients, initializer, sync_type, name); CHECK_IS_JSONABLE(V1Tensor); + V1Tensor to_v1(Tensor const &); } // namespace FlexFlow diff --git a/lib/pcg/include/pcg/file_format/v1/v1.h b/lib/pcg/include/pcg/file_format/v1/v1.h index e2557af4f5..afaa4f08b9 100644 --- a/lib/pcg/include/pcg/file_format/v1/v1.h +++ b/lib/pcg/include/pcg/file_format/v1/v1.h @@ -4,6 +4,17 @@ #include "graphs.h" #include "pcg/computation_graph.h" -namespace FlexFlow {} +namespace FlexFlow { + +template +optional to_v1(optional const &t) { + if (t.has_value()) { + return to_v1(t.value()); + } else { + return nullopt; + } +} + +} // namespace FlexFlow #endif diff --git a/lib/pcg/include/pcg/layer.h b/lib/pcg/include/pcg/layer.h index 6e9415a8fb..e17eef3875 100644 --- a/lib/pcg/include/pcg/layer.h +++ b/lib/pcg/include/pcg/layer.h @@ -7,16 +7,14 @@ namespace FlexFlow { -struct Layer : public use_visitable_cmp { +struct Layer { public: - Layer() = delete; - Layer(CompGraphOperatorAttrs const &attrs, optional const &name); - -public: - optional> name; - CompGraphOperatorAttrs attrs; + req attrs; + req>> name; }; +FF_VISITABLE_STRUCT(Layer, attrs, name); + } // namespace FlexFlow VISITABLE_STRUCT(::FlexFlow::Layer, attrs, name); diff --git a/lib/pcg/include/pcg/operator.h b/lib/pcg/include/pcg/operator.h index c7a49bb57e..1f5a004680 100644 --- a/lib/pcg/include/pcg/operator.h +++ b/lib/pcg/include/pcg/operator.h @@ -8,24 +8,17 @@ namespace FlexFlow { -struct Operator : public use_visitable_cmp { +struct Operator { public: - Operator() = delete; - Operator(PCGOperatorAttrs const &attrs, optional const &name); - operator PCGOperatorAttrs() const; public: - PCGOperatorAttrs attrs; + req attrs; + req>> name; }; -} // namespace FlexFlow - -VISITABLE_STRUCT(::FlexFlow::Operator, attrs); -MAKE_VISIT_HASHABLE(::FlexFlow::Operator); +FF_VISITABLE_STRUCT(Operator, attrs, name); -namespace FlexFlow { -static_assert(is_well_behaved_value_type::value, ""); -} +} // namespace FlexFlow #endif diff --git a/lib/pcg/include/pcg/parallel_tensor.h b/lib/pcg/include/pcg/parallel_tensor.h index eadc83d9fd..1a83edc93f 100644 --- a/lib/pcg/include/pcg/parallel_tensor.h +++ b/lib/pcg/include/pcg/parallel_tensor.h @@ -50,9 +50,10 @@ struct ParallelTensor : public use_visitable_cmp { public: ParallelTensorDims dims; DataType data_type; + CreateGrad create_gradients; optional sync_type = nullopt; optional initializer = nullopt; - CreateGrad create_gradients; + optional name = nullopt; }; using ParallelParameter = ParallelTensor; @@ -64,11 +65,8 @@ VISITABLE_STRUCT(::FlexFlow::ParallelTensor, data_type, sync_type, initializer, - create_gradients); + create_gradients, + name); MAKE_VISIT_HASHABLE(::FlexFlow::ParallelTensor); -namespace FlexFlow { -static_assert(is_well_behaved_value_type::value, ""); -} - #endif diff --git a/lib/pcg/include/pcg/tensor.h b/lib/pcg/include/pcg/tensor.h index cb79be245a..706516bd15 100644 --- a/lib/pcg/include/pcg/tensor.h +++ b/lib/pcg/include/pcg/tensor.h @@ -9,12 +9,6 @@ namespace FlexFlow { struct Tensor { - /* Tensor() = delete; */ - /* Tensor(TensorShape const &, */ - /* CreateGrad create_gradients, */ - /* optional initializer = nullopt, */ - /* optional sync_type = nullopt); */ - size_t get_volume() const; TensorShape get_shape() const; int num_dims() const; @@ -24,12 +18,13 @@ struct Tensor { public: TensorDims dims; DataType data_type; - req> initializer; req create_gradients; + req> initializer; req> sync_type; + req> name; }; FF_VISITABLE_STRUCT( - Tensor, dims, data_type, initializer, create_gradients, sync_type); + Tensor, dims, data_type, create_gradients, initializer, sync_type, name); using Parameter = Tensor; diff --git a/lib/pcg/src/file_format/v1/graphs.cc b/lib/pcg/src/file_format/v1/graphs.cc index 519c38448b..0ad71b3ab4 100644 --- a/lib/pcg/src/file_format/v1/graphs.cc +++ b/lib/pcg/src/file_format/v1/graphs.cc @@ -55,4 +55,8 @@ V1ComputationGraph to_v1(ComputationGraph const &g) { return to_v1(g.value()); } +V1ParallelComputationGraph to_v1(ParallelComputationGraph const &g) { + return to_v1(g.value()); +} + } // namespace FlexFlow diff --git a/lib/pcg/src/file_format/v1/tensor.cc b/lib/pcg/src/file_format/v1/tensor.cc new file mode 100644 index 0000000000..55bc71ce0d --- /dev/null +++ b/lib/pcg/src/file_format/v1/tensor.cc @@ -0,0 +1,16 @@ +#include "pcg/file_format/v1/tensor.h" +#include "pcg/file_format/v1/v1.h" + +namespace FlexFlow { + +V1Tensor to_v1(Tensor const &t) { + return { + to_v1(t.get_shape()), + t.create_gradients, + to_v1(t.initializer), + to_v1(t.sync_type), + t.name, + }; +} + +} // namespace FlexFlow diff --git a/lib/pcg/src/layer.cc b/lib/pcg/src/layer.cc deleted file mode 100644 index 27d5b31003..0000000000 --- a/lib/pcg/src/layer.cc +++ /dev/null @@ -1,9 +0,0 @@ -#include "pcg/layer.h" - -namespace FlexFlow { - -Layer::Layer(CompGraphOperatorAttrs const &_attrs, - optional const &_name) - : attrs(_attrs), name(_name) {} - -} // namespace FlexFlow diff --git a/lib/pcg/test/CMakeLists.txt b/lib/pcg/test/CMakeLists.txt new file mode 100644 index 0000000000..df1321f05f --- /dev/null +++ b/lib/pcg/test/CMakeLists.txt @@ -0,0 +1,28 @@ +set(test_target pcg-test) +project(${test_target}) + +file(GLOB_RECURSE SRC + CONFIGURE_DEPENDS + LIST_DIRECTORIES False + *.cc) + +add_executable( + ${test_target} + ${SRC}) + +define_ff_vars(${test_target}) + +target_link_libraries( + ${test_target} + pcg + utils + doctest::doctest) + +set_target_properties( + ${test_target} + PROPERTIES + CXX_STANDARD 11 + CXX_STANDARD_REQUIRED YES + CXX_EXTENSIONS NO +) +doctest_discover_tests(${test_target}) diff --git a/lib/pcg/test/doctest.h b/lib/pcg/test/doctest.h new file mode 100644 index 0000000000..891cc81d32 --- /dev/null +++ b/lib/pcg/test/doctest.h @@ -0,0 +1,70 @@ +#include "doctest/doctest.h" +#include "utils/containers.h" +#include +#include +#include +#include + +namespace doctest { + +template +std::string + doctest_print_container(InputIt first, + InputIt last, + std::string const &open, + std::string const &delimiter, + std::string const &close, + std::function const &f) { + if (first == last) { + return open + "(empty)" + close; + } else { + return open + join_strings(first, last, delimiter, f) + close; + } +} + +template +std::string doctest_print_container(InputIt first, + InputIt last, + std::string const &open, + std::string const &delimiter, + std::string const &close) { + return doctest_print_container( + first, last, open, delimiter, close, [](InputIt ref) { return *ref; }); +} + +template +std::string doctest_print_container(Container const &c, + std::string const &open, + std::string const &delimiter, + std::string const &close) { + return doctest_print_container( + c.cbegin(), c.cend(), open, delimiter, close); +} + +template +struct StringMaker> { + static String convert(std::unordered_set const &s) { + return doctest_print_container(s, "{ ", ", ", " }").c_str(); + } +}; + +template +struct StringMaker> { + static String convert(std::unordered_map const &m) { + std::unordered_set entries; + for (auto const &kv : m) { + std::ostringstream oss; + oss << toString(kv.first) << " -> " << toString(kv.second); + entries.insert(oss.str()); + } + return toString(entries); + } +}; + +template +struct StringMaker> { + static String convert(std::vector const &vec) { + return doctest_print_container(vec, "[ ", ", ", " ]").c_str(); + } +}; +} // namespace doctest diff --git a/lib/pcg/test/main.cc b/lib/pcg/test/main.cc new file mode 100644 index 0000000000..9522fa7fdb --- /dev/null +++ b/lib/pcg/test/main.cc @@ -0,0 +1,2 @@ +#define DOCTEST_CONFIG_IMPLEMENT_WITH_MAIN +#include "doctest/doctest.h" diff --git a/lib/pcg/test/test_tensor.cc b/lib/pcg/test/test_tensor.cc new file mode 100644 index 0000000000..0a15fd22e1 --- /dev/null +++ b/lib/pcg/test/test_tensor.cc @@ -0,0 +1,14 @@ +#include "doctest.h" +#include "pcg/file_format/v1/tensor.h" +#include "pcg/tensor.h" +#include "utils/containers.h" +#include "utils/required.h" + +#include + +using namespace FlexFlow; + +TEST_CASE("Tensor") { + Tensor t{{3, 4, 5}, DataType::FLOAT, false, nullopt, nullopt, std::string("tensor")}; + to_v1(t); +} diff --git a/lib/utils/include/utils/graph/algorithms.h b/lib/utils/include/utils/graph/algorithms.h index 9f1d2e12d5..ed18d6e1c5 100644 --- a/lib/utils/include/utils/graph/algorithms.h +++ b/lib/utils/include/utils/graph/algorithms.h @@ -233,6 +233,8 @@ tl::optional get_imm_post_dominator(MultiDiGraphView const &, Node const &); tl::optional get_imm_post_dominator(DiGraphView const &, std::unordered_set const &); +tl::optional get_imm_post_dominator(MultiDiGraphView const &, + std::unordered_set const &); std::vector get_dfs_ordering(DiGraphView const &, diff --git a/lib/utils/include/utils/graph/cow_ptr_t.h b/lib/utils/include/utils/graph/cow_ptr_t.h index 9a655ae072..3c5cf6ed10 100644 --- a/lib/utils/include/utils/graph/cow_ptr_t.h +++ b/lib/utils/include/utils/graph/cow_ptr_t.h @@ -11,8 +11,8 @@ namespace FlexFlow { template struct cow_ptr_t { - static_assert(is_clonable::value, - "cow_ptr_t requires the type to have a clone() method"); + // static_assert(is_clonable::value, + // "cow_ptr_t requires the type to have a clone() method"); cow_ptr_t(std::shared_ptr const &ptr) : ptr(ptr) {} cow_ptr_t(std::shared_ptr &&ptr) : ptr(std::move(ptr)) {} diff --git a/lib/utils/include/utils/graph/multidigraph.h b/lib/utils/include/utils/graph/multidigraph.h index 77bd3aedea..deb32fceb0 100644 --- a/lib/utils/include/utils/graph/multidigraph.h +++ b/lib/utils/include/utils/graph/multidigraph.h @@ -47,6 +47,7 @@ struct MultiDiGraph { MultiDiGraph() = delete; MultiDiGraph(MultiDiGraph const &) = default; MultiDiGraph &operator=(MultiDiGraph const &) = default; + virtual ~MultiDiGraph() = default; operator MultiDiGraphView() const; diff --git a/lib/utils/include/utils/graph/multidigraph_interfaces.h b/lib/utils/include/utils/graph/multidigraph_interfaces.h index 291021ae6b..1fcd83903c 100644 --- a/lib/utils/include/utils/graph/multidigraph_interfaces.h +++ b/lib/utils/include/utils/graph/multidigraph_interfaces.h @@ -52,6 +52,7 @@ struct IMultiDiGraph : public IMultiDiGraphView, public IGraph { } virtual IMultiDiGraph *clone() const override = 0; + virtual ~IMultiDiGraph() = default; }; CHECK_RC_COPY_VIRTUAL_COMPLIANT(IMultiDiGraph); diff --git a/lib/utils/src/graph/adjacency_digraph.cc b/lib/utils/src/graph/adjacency_digraph.cc index 1438edc78b..e750d32c42 100644 --- a/lib/utils/src/graph/adjacency_digraph.cc +++ b/lib/utils/src/graph/adjacency_digraph.cc @@ -3,6 +3,10 @@ namespace FlexFlow { +AdjacencyDiGraph::AdjacencyDiGraph(std::size_t, ContentsType const&) { + NOT_IMPLEMENTED(); +} + Node AdjacencyDiGraph::add_node() { Node node{this->next_node_idx}; adjacency[node]; diff --git a/lib/utils/src/graph/adjacency_multidigraph.cc b/lib/utils/src/graph/adjacency_multidigraph.cc index 79e7de7d75..0b883a441f 100644 --- a/lib/utils/src/graph/adjacency_multidigraph.cc +++ b/lib/utils/src/graph/adjacency_multidigraph.cc @@ -3,6 +3,11 @@ namespace FlexFlow { +AdjacencyMultiDiGraph::AdjacencyMultiDiGraph(std::size_t, + ContentsType const &) { + NOT_IMPLEMENTED(); +} + Node AdjacencyMultiDiGraph::add_node() { Node node{this->next_node_idx}; adjacency[node]; diff --git a/lib/utils/src/graph/algorithms.cc b/lib/utils/src/graph/algorithms.cc index d261fc6be7..0543fc89b5 100644 --- a/lib/utils/src/graph/algorithms.cc +++ b/lib/utils/src/graph/algorithms.cc @@ -506,6 +506,23 @@ std::unordered_map> std::unordered_map> get_imm_dominators(DiGraphView const &g) { + std::unordered_map topo_rank = [&g]() { + std::vector topo_ordering = get_topological_ordering(g); + std::unordered_map topo_rank; + for (int i = 0; i < topo_ordering.size(); i++) { + topo_rank[topo_ordering[i]] = i; + } + return topo_rank; + }(); + + auto with_greatest_topo_rank = + [&topo_rank](std::unordered_set const &nodes) -> Node { + return *std::max_element(nodes.cbegin(), + nodes.cend(), + [&topo_rank](Node const &lhs, Node const &rhs) { + return topo_rank.at(lhs) < topo_rank.at(rhs); + }); + }; std::unordered_map> result; for (auto const &kv : get_dominators(g)) { diff --git a/lib/utils/src/graph/digraph.cc b/lib/utils/src/graph/digraph.cc index 341005bd08..4c85362841 100644 --- a/lib/utils/src/graph/digraph.cc +++ b/lib/utils/src/graph/digraph.cc @@ -5,6 +5,11 @@ namespace FlexFlow { +DirectedEdgeQuery query_intersection(DirectedEdgeQuery const &lhs, + DirectedEdgeQuery const &rhs) { + NOT_IMPLEMENTED(); +} + void swap(DiGraph &lhs, DiGraph &rhs) { using std::swap; @@ -104,4 +109,16 @@ DiGraph::operator DiGraphView() const { DiGraphView::DiGraphView(std::shared_ptr ptr) : ptr(ptr) {} +DiGraph::operator DiGraphView() const { + return DiGraphView(this->ptr.get()); +} + +DiGraphView::DiGraphView(std::shared_ptr) { + NOT_IMPLEMENTED(); +} + +DiGraphView::operator GraphView() const { + NOT_IMPLEMENTED(); +} + } // namespace FlexFlow From aade00cea3773e495a12fad06abb1cfe8b38c99a Mon Sep 17 00:00:00 2001 From: Colin Unger Date: Thu, 31 Aug 2023 23:45:47 -0700 Subject: [PATCH 02/15] Add partial required fix --- lib/utils/include/utils/required.h | 32 +++-- lib/utils/include/utils/required_core.h | 115 ++++++++++++++--- lib/utils/include/utils/test_types.h | 42 ++++++- lib/utils/include/utils/type_traits.h | 81 ------------ lib/utils/include/utils/type_traits_core.h | 118 ++++++++++++++++++ .../test/common/include/test/utils/doctest.h | 4 + lib/utils/test/src/test_required.cc | 92 ++++++++++++++ 7 files changed, 369 insertions(+), 115 deletions(-) create mode 100644 lib/utils/test/src/test_required.cc diff --git a/lib/utils/include/utils/required.h b/lib/utils/include/utils/required.h index 499994770a..4165b442fa 100644 --- a/lib/utils/include/utils/required.h +++ b/lib/utils/include/utils/required.h @@ -24,24 +24,34 @@ struct adl_serializer<::FlexFlow::req> { }; } // namespace nlohmann -namespace fmt { +/* namespace fmt { */ -template -struct formatter<::FlexFlow::req> : formatter { - template - auto format(::FlexFlow::req const &t, FormatContext &ctx) - -> decltype(ctx.out()) { - return formatter::format(static_cast(t), ctx); - } -}; +/* template */ +/* struct formatter<::FlexFlow::req> : formatter { */ +/* template */ +/* auto format(::FlexFlow::req const &t, FormatContext &ctx) */ +/* -> decltype(ctx.out()) { */ +/* return formatter::format(static_cast(t), ctx); */ +/* } */ +/* }; */ -} // namespace fmt +/* } // namespace fmt */ namespace FlexFlow { static_assert(is_json_serializable>::value, ""); static_assert(is_json_deserializable>::value, ""); static_assert(is_jsonable>::value, ""); -static_assert(is_fmtable>::value, ""); +CHECK_FMTABLE(req); +CHECK_FMTABLE(std::vector); +CHECK_FMTABLE(required_inheritance_impl>); +static_assert( + std::is_base_of< + required_inheritance_impl>, + req> + >::value, "" +); +CHECK_FMTABLE(req>); + } // namespace FlexFlow #endif diff --git a/lib/utils/include/utils/required_core.h b/lib/utils/include/utils/required_core.h index 3336e38243..8d20597efc 100644 --- a/lib/utils/include/utils/required_core.h +++ b/lib/utils/include/utils/required_core.h @@ -4,9 +4,22 @@ #include "hash-utils-core.h" #include "type_traits_core.h" #include +#include "test_types.h" +#include "fmt.decl.h" namespace FlexFlow { +template +struct enable_if_valid {}; + +template +struct enable_if_valid, Args...> : type_identity {}; + +/* required_wrapper_impl() + std::declval())>> */ +/* operator+(required_wrapper_impl const &lhs, required_wrapper_impl const &rhs) { */ +/* /1* return 1; *1/ */ +/* } */ + template struct required_wrapper_impl { public: @@ -34,6 +47,10 @@ struct required_wrapper_impl { return static_cast(this->m_value); } + friend T format_as(required_wrapper_impl const &r) { + return static_cast(r); + } + /* T const &operator*() const { */ /* return this->m_value; */ /* } */ @@ -42,12 +59,54 @@ struct required_wrapper_impl { /* return &this->m_value; */ /* } */ - /* bool operator==(T const &other) const { */ - /* return this->m_value == other; */ + template + enable_if_t::value, bool> + operator==(required_wrapper_impl const &rhs) const { + return this->m_value == rhs.m_value; + } + + template + enable_if_t::value, bool> + operator==(TT const &rhs) const { + return this->m_value == rhs; + } + + /* friend enable_if_t::value, bool> */ + /* operator==(required_wrapper_impl const &lhs, T const &rhs) { */ + /* return lhs.m_value == rhs; */ + /* } */ + + /* friend enable_if_t::value, bool> */ + /* operator==(T const &lhs, required_wrapper_impl const &rhs) { */ + /* return lhs == rhs.m_value; */ + /* } */ + + template + enable_if_t::value, bool> + operator!=(required_wrapper_impl const &rhs) const { + return this->m_value != rhs.m_value; + } + + /* friend enable_if_t::value, required_wrapper_impl() + std::declval())>> */ + /* operator+(required_wrapper_impl const &lhs, required_wrapper_impl const &rhs) { */ + /* /1* return 1; *1/ */ + /* } */ + /* required_wrapper_impl */ + /* operator+(required_wrapper_impl const &rhs) { */ + /* Out o = this->m_value + rhs.m_value; */ + /* return required_wrapper_impl{o}; */ /* } */ - /* bool operator!=(T const &other) const { */ - /* return this->m_value != other; */ + /* template ::value> = true> */ + /* required_wrapper_impl operator-(required_wrapper_impl const &rhs) { */ + /* return {this->m_value - rhs.m_value}; */ + /* } */ + + /* template ::value> = true> */ + /* required_wrapper_impl operator*(required_wrapper_impl const &rhs) { */ + /* return {this->m_value * rhs.m_value}; */ /* } */ /* bool operator<(T const &other) const { */ @@ -68,8 +127,31 @@ struct required_inheritance_impl : public T { using T::T; required_inheritance_impl() = delete; - required_inheritance_impl(T const &); - required_inheritance_impl(T &&t); + required_inheritance_impl(T const &t) : T(t) {} + required_inheritance_impl(T &&t) : T(t) {} + + required_inheritance_impl(required_inheritance_impl const &) = default; + required_inheritance_impl(required_inheritance_impl &&) = default; + + required_inheritance_impl &operator=(required_inheritance_impl const &) = default; + required_inheritance_impl &operator=(required_inheritance_impl &&) = default; + + friend enable_if_t::value, bool> + operator==(required_inheritance_impl const &lhs, required_inheritance_impl const &rhs) { + return static_cast(lhs) == static_cast(rhs); + } + + friend enable_if_t::value, bool> + operator!=(required_inheritance_impl const &lhs, required_inheritance_impl const &rhs) { + return static_cast(lhs) != static_cast(rhs); + } + + friend std::string format_as(required_inheritance_impl const &r) { + return ""; + /* static_assert(is_fmtable::value, ""); */ + + /* return static_cast(r); */ + } template required_inheritance_impl( @@ -78,8 +160,6 @@ struct required_inheritance_impl : public T { !std::is_same::value>::type * = 0) : required_inheritance_impl(static_cast(tt)) {} - operator T() const; - template ::value && !std::is_same::value), @@ -116,19 +196,16 @@ struct remove_req> { template using remove_req_t = typename remove_req::type; +static_assert(is_equal_comparable>>::value, ""); +CHECK_WELL_BEHAVED_VALUE_TYPE_NO_HASH(required_inheritance_impl); +CHECK_WELL_BEHAVED_VALUE_TYPE_NO_HASH(required_wrapper_impl); + +/* static_assert(std::is_same>() + std::declval>()), required_wrapper_impl>::value, ""); */ + +static_assert(std::is_copy_constructible>::value, ""); + static_assert(std::is_convertible, int>::value, ""); static_assert(is_static_castable, int *>::value, ""); -static_assert( - std::is_same< - void_t>() == std::declval())>, - void>::value, - ""); -static_assert(is_list_initializable, bool>::value, ""); -static_assert( - std::is_same< - void_t>() + std::declval())>, - void>::value, - ""); } // namespace FlexFlow diff --git a/lib/utils/include/utils/test_types.h b/lib/utils/include/utils/test_types.h index 2cac547bb6..308bd61428 100644 --- a/lib/utils/include/utils/test_types.h +++ b/lib/utils/include/utils/test_types.h @@ -1,7 +1,7 @@ #ifndef _FLEXFLOW_UTILS_INCLUDE_UTILS_TEST_TYPES_H #define _FLEXFLOW_UTILS_INCLUDE_UTILS_TEST_TYPES_H -#include "type_traits.h" +#include "type_traits_core.h" namespace FlexFlow { @@ -12,7 +12,10 @@ enum capability { EQ, CMP, DEFAULT_CONSTRUCTIBLE, - COPYABLE, + MOVE_CONSTRUCTIBLE, + MOVE_ASSIGNABLE, + COPY_CONSTRUCTIBLE, + COPY_ASSIGNABLE, PLUS, PLUSEQ, FMT @@ -51,14 +54,38 @@ struct test_type_t { typename std::enable_if::value, bool>::type = true> test_type_t() = delete; - template ::value, bool>::type = true> test_type_t(test_type_t const &); - template ::value, bool>::type = true> test_type_t(test_type_t const &) = delete; + template ::value, bool>::type = true> + test_type_t &operator=(test_type_t const &); + + template ::value, bool>::type = true> + test_type_t &operator=(test_type_t const &) = delete; + + template ::value, bool>::type = true> + test_type_t(test_type_t &&); + + template ::value, bool>::type = true> + test_type_t(test_type_t &&) = delete; + + template ::value, bool>::type = true> + test_type_t &operator=(test_type_t &&); + + template ::value, bool>::type = true> + test_type_t &operator=(test_type_t &&) = delete; + template typename std::enable_if::value, bool>::type operator==(test_type_t const &) const; @@ -102,6 +129,13 @@ using cmp = test_type_t; using hash_cmp = test_type_t; using plusable = test_type_t; using fmtable = test_type_t; +using well_behaved_value_type = test_type_t< + EQ, + COPY_CONSTRUCTIBLE, + MOVE_CONSTRUCTIBLE, + COPY_ASSIGNABLE, + MOVE_ASSIGNABLE +>; } // namespace test_types } // namespace FlexFlow diff --git a/lib/utils/include/utils/type_traits.h b/lib/utils/include/utils/type_traits.h index dc8fe2cf57..ee45e8dc2e 100644 --- a/lib/utils/include/utils/type_traits.h +++ b/lib/utils/include/utils/type_traits.h @@ -65,24 +65,6 @@ template struct is_streamable())>> : std::true_type {}; -template -struct is_equal_comparable : std::false_type {}; - -template -struct is_equal_comparable< - T, - void_t() == std::declval()))>> - : std::true_type {}; - -template -struct is_neq_comparable : std::false_type {}; - -template -struct is_neq_comparable< - T, - void_t() != std::declval()))>> - : std::true_type {}; - template struct is_lt_comparable : std::false_type {}; @@ -92,19 +74,6 @@ struct is_lt_comparable< void_t() < std::declval()))>> : std::true_type {}; -template -struct is_hashable : std::false_type {}; - -template -struct is_hashable< - T, - void_t>()(std::declval())))>> - : std::true_type {}; - -#define CHECK_HASHABLE(...) \ - static_assert(is_hashable<__VA_ARGS__>::value, \ - #__VA_ARGS__ " should be hashable (but is not)"); - template