]> git.tdb.fi Git - libs/game.git/commitdiff
Refactor dependency iteration in SystemScheduler to be more reusable
authorMikko Rasa <tdb@tdb.fi>
Sun, 23 Mar 2025 11:16:12 +0000 (13:16 +0200)
committerMikko Rasa <tdb@tdb.fi>
Sun, 23 Mar 2025 11:18:22 +0000 (13:18 +0200)
source/game/systemscheduler.cpp
source/game/systemscheduler.h

index 1cc78a4330276d0c25b589beb0f33379dd27e2a9..0a15a300d1b6551dc6b24d63b6e5408224e99c20 100644 (file)
@@ -70,6 +70,46 @@ int SystemScheduler::get_data_order(const GraphNode &node1, const GraphNode &nod
        int data_order = 0;
        const Reflection::ClassBase *ordered_data = nullptr;
        const Reflection::ClassBase *unordered_data = nullptr;
+       for_common_deps(node1, node2, [&](const Reflection::ClassBase *type, int flags1, int flags2){
+               bool unbuffered = (flags1|flags2)&System::UNBUFFERED;
+               flags1 &= ~System::UNBUFFERED;
+               flags2 &= ~System::UNBUFFERED;
+
+               int order = 0;
+               // Read-only access to fresh data comes after any writes
+               if(flags1==System::READ_FRESH && (flags2&System::WRITE))
+                       order = 1;
+               else if(flags2==System::READ_FRESH && (flags1&System::WRITE))
+                       order = -1;
+               // Reads can happen concurrently to other access with buffering
+               else if(!(flags1&flags2&System::WRITE) && !unbuffered)
+                       order = 0;
+               // Chained updates always come after non-chained writes
+               else if(flags1==System::CHAINED_UPDATE && (flags2==System::WRITE || flags2==System::UPDATE))
+                       order = 1;
+               else if(flags2==System::CHAINED_UPDATE && (flags1==System::WRITE || flags1==System::UPDATE))
+                       order = -1;
+               else
+                       unordered_data = type;
+
+               if(order && data_order && order!=data_order)
+                       throw scheduling_error(format("Ambiguous data ordering between %s and %s, accessing %s and %s",
+                               node1.type->get_name(), node2.type->get_name(), ordered_data->get_name(), type->get_name()));
+
+               data_order = order;
+               ordered_data = type;
+       });
+
+       if(!data_order && unordered_data)
+               throw scheduling_error(format("Ambiguous data ordering between %s and %s, accessing %s",
+                       node1.type->get_name(), node2.type->get_name(), unordered_data->get_name()));
+
+       return data_order;
+}
+
+template<typename F>
+void SystemScheduler::for_common_deps(const GraphNode &node1, const GraphNode &node2, const F &func)
+{
        for(const System::Dependency &d1: node1.system->get_dependencies())
        {
                int flags1 = d1.get_flags()&System::DATA_MASK;
@@ -90,41 +130,9 @@ int SystemScheduler::get_data_order(const GraphNode &node1, const GraphNode &nod
                        else
                                continue;
 
-                       bool unbuffered = (flags1|flags2)&System::UNBUFFERED;
-                       flags1 &= ~System::UNBUFFERED;
-                       flags2 &= ~System::UNBUFFERED;
-
-                       int order = 0;
-                       // Read-only access to fresh data comes after any writes
-                       if(flags1==System::READ_FRESH && (flags2&System::WRITE))
-                               order = 1;
-                       else if(flags2==System::READ_FRESH && (flags1&System::WRITE))
-                               order = -1;
-                       // Reads can happen concurrently to other access with buffering
-                       else if(!(flags1&flags2&System::WRITE) && !unbuffered)
-                               order = 0;
-                       // Chained updates always come after non-chained writes
-                       else if(flags1==System::CHAINED_UPDATE && (flags2==System::WRITE || flags2==System::UPDATE))
-                               order = 1;
-                       else if(flags2==System::CHAINED_UPDATE && (flags1==System::WRITE || flags1==System::UPDATE))
-                               order = -1;
-                       else
-                               unordered_data = common_type;
-
-                       if(order && data_order && order!=data_order)
-                               throw scheduling_error(format("Ambiguous data ordering between %s and %s, accessing %s and %s",
-                                       node1.type->get_name(), node2.type->get_name(), ordered_data->get_name(), common_type->get_name()));
-
-                       data_order = order;
-                       ordered_data = common_type;
+                       func(common_type, flags1, flags2);
                }
        }
-
-       if(!data_order && unordered_data)
-               throw scheduling_error(format("Ambiguous data ordering between %s and %s, accessing %s",
-                       node1.type->get_name(), node2.type->get_name(), unordered_data->get_name()));
-
-       return data_order;
 }
 
 void SystemScheduler::run(Time::TimeDelta dt)
index 9101f810c95fe8342985dd93139824e03a847e9f..f7c1ebd43e8c974a9700dc4a7eed9ce3b3407de1 100644 (file)
@@ -44,6 +44,8 @@ private:
        static int get_order(const GraphNode &, const GraphNode &);
        static int get_explicit_order(const GraphNode &, const GraphNode &);
        static int get_data_order(const GraphNode &, const GraphNode &);
+       template<typename F>
+       static void for_common_deps(const GraphNode &, const GraphNode &, const F &);
 
 public:
        const std::vector<GraphNode> &get_graph() const { return nodes; }