]> git.ipfire.org Git - thirdparty/kea.git/commitdiff
[#3262] on completion callback for subnet select
authorAndrei Pavel <andrei@isc.org>
Wed, 6 Mar 2024 16:24:37 +0000 (18:24 +0200)
committerAndrei Pavel <andrei@isc.org>
Mon, 18 Mar 2024 09:33:11 +0000 (11:33 +0200)
src/bin/dhcp4/dhcp4_lexer.ll
src/bin/dhcp4/dhcp4_srv.cc
src/bin/dhcp6/dhcp6_srv.cc

index d4799108f6e7a1af4920b9df20ecb7f4ce9cb4e4..30db220e0eafbb461d525d271c70bc069872428f 100644 (file)
@@ -1,4 +1,4 @@
-/* Copyright (C) 2016-2023 Internet Systems Consortium, Inc. ("ISC")
+/* Copyright (C) 2016-2024 Internet Systems Consortium, Inc. ("ISC")
 
    This Source Code Form is subject to the terms of the Mozilla Public
    License, v. 2.0. If a copy of the MPL was not distributed with this
index 80bba69d43cf702c0911d80295bfcd80e321e616..4f4279a9c15da6b176bc0bea85a8c5ed372ebf64 100644 (file)
@@ -744,7 +744,8 @@ Dhcpv4Srv::selectSubnet(const Pkt4Ptr& query, bool& drop,
         // reset when this object goes out of scope. All hook points must do
         // it to prevent possible circular dependency between the callout
         // handle and its arguments.
-        ScopedCalloutHandleState callout_handle_state(callout_handle);
+        shared_ptr<ScopedCalloutHandleState> callout_handle_state(
+            std::make_shared<ScopedCalloutHandleState>(callout_handle));
 
         // Enable copying options from the packet within hook library.
         ScopedEnableOptionsCopy<Pkt4> query4_options_copy(query);
@@ -757,13 +758,21 @@ Dhcpv4Srv::selectSubnet(const Pkt4Ptr& query, bool& drop,
                                     getCfgSubnets4()->getAll());
 
         // We proactively park the packet.
-        // Not MT compatible because the unparking callback can be called
-        // before the current thread exists from this block.
-        HooksManager::park("subnet4_select", query,
-                           [this, query, allow_answer_park] () {
-                               processLocalizedQuery4AndSendResponse(query,
-                                                                     allow_answer_park);
-                           });
+        HooksManager::park(
+            "subnet4_select", query, [this, query, allow_answer_park, callout_handle_state]() {
+                if (MultiThreadingMgr::instance().getMode()) {
+                    boost::shared_ptr<function<void()>> callback(
+                        boost::make_shared<function<void()>>(
+                            [this, query, allow_answer_park]() mutable {
+                                processLocalizedQuery4AndSendResponse(query, allow_answer_park);
+                            }));
+                    callout_handle_state->on_completion_ = [callback]() {
+                        MultiThreadingMgr::instance().getThreadPool().add(callback);
+                    };
+                } else {
+                    processLocalizedQuery4AndSendResponse(query, allow_answer_park);
+                }
+            });
 
         // Call user (and server-side) callouts
         try {
@@ -891,7 +900,8 @@ Dhcpv4Srv::selectSubnet4o6(const Pkt4Ptr& query, bool& drop,
         // reset when this object goes out of scope. All hook points must do
         // it to prevent possible circular dependency between the callout
         // handle and its arguments.
-        ScopedCalloutHandleState callout_handle_state(callout_handle);
+        shared_ptr<ScopedCalloutHandleState> callout_handle_state(
+            std::make_shared<ScopedCalloutHandleState>(callout_handle));
 
         // Enable copying options from the packet within hook library.
         ScopedEnableOptionsCopy<Pkt4> query4_options_copy(query);
@@ -904,13 +914,21 @@ Dhcpv4Srv::selectSubnet4o6(const Pkt4Ptr& query, bool& drop,
                                     getCfgSubnets4()->getAll());
 
         // We proactively park the packet.
-        // Not MT compatible because the unparking callback can be called
-        // before the current thread exists from this block.
-        HooksManager::park("subnet4_select", query,
-                           [this, query, allow_answer_park] () {
-                               processLocalizedQuery4AndSendResponse(query,
-                                                                     allow_answer_park);
-                           });
+        HooksManager::park(
+            "subnet4_select", query, [this, query, allow_answer_park, callout_handle_state]() {
+                if (MultiThreadingMgr::instance().getMode()) {
+                    boost::shared_ptr<function<void()>> callback(
+                        boost::make_shared<function<void()>>(
+                            [this, query, allow_answer_park]() mutable {
+                                processLocalizedQuery4AndSendResponse(query, allow_answer_park);
+                            }));
+                    callout_handle_state->on_completion_ = [callback]() {
+                        MultiThreadingMgr::instance().getThreadPool().add(callback);
+                    };
+                } else {
+                    processLocalizedQuery4AndSendResponse(query, allow_answer_park);
+                }
+            });
 
         // Call user (and server-side) callouts
         try {
index b4db600e5e532228193f88c3e7441d0c08eef898..574e6b04423af27ccfec88f6b6764d05fd9e08ac 100644 (file)
@@ -993,6 +993,7 @@ Dhcpv6Srv::processDhcp6Query(Pkt6Ptr query) {
     return (processLocalizedQuery6(ctx));
 }
 
+
 void
 Dhcpv6Srv::processLocalizedQuery6AndSendResponse(Pkt6Ptr query,
                                                  AllocEngine::ClientContext6& ctx) {
@@ -2005,7 +2006,8 @@ Dhcpv6Srv::selectSubnet(const Pkt6Ptr& question, bool& drop) {
         // reset when this object goes out of scope. All hook points must do
         // it to prevent possible circular dependency between the callout
         // handle and its arguments.
-        ScopedCalloutHandleState callout_handle_state(callout_handle);
+        shared_ptr<ScopedCalloutHandleState> callout_handle_state(
+            std::make_shared<ScopedCalloutHandleState>(callout_handle));
 
         // Enable copying options from the packet within hook library.
         ScopedEnableOptionsCopy<Pkt6> query6_options_copy(question);
@@ -2024,10 +2026,19 @@ Dhcpv6Srv::selectSubnet(const Pkt6Ptr& question, bool& drop) {
         // We proactively park the packet.
         // Not MT compatible because the unparking callback can be called
         // before the current thread exists from this block.
-        HooksManager::park("subnet6_select", question,
-                           [this, question] () {
-                               processLocalizedQuery6AndSendResponse(question);
-                           });
+        HooksManager::park("subnet6_select", question, [this, question, callout_handle_state]() {
+            if (MultiThreadingMgr::instance().getMode()) {
+                boost::shared_ptr<function<void()>> callback(
+                    boost::make_shared<function<void()>>([this, question]() mutable {
+                        processLocalizedQuery6AndSendResponse(question);
+                    }));
+                callout_handle_state->on_completion_ = [callback]() {
+                    MultiThreadingMgr::instance().getThreadPool().add(callback);
+                };
+            } else {
+                processLocalizedQuery6AndSendResponse(question);
+            }
+        });
 
         // Call user (and server-side) callouts
         try {