Browse code

client-connect: Implement deferred connect support for plugin API v2

The V2 API is simpler than the V1 API since there is no passing of
data via files. This also means that with the current API the V2 API
cannot support async notify via files. Adding a file just for async
notify seems very hacky and when needed we should implement a better
option when async is needed for the plugin V2 API.

Signed-off-by: Arne Schwabe <arne@rfc2549.org>
Acked-by: Gert Doering <gert@greenie.muc.de>
Message-Id: <20200719173436.16431-5-arne@rfc2549.org>
URL: https://www.mail-archive.com/openvpn-devel@lists.sourceforge.net/msg20480.html
Signed-off-by: Gert Doering <gert@greenie.muc.de>

Arne Schwabe authored on 2020/07/20 02:34:36
Showing 3 changed files
... ...
@@ -130,7 +130,8 @@ extern "C" {
130 130
 #define OPENVPN_PLUGIN_ENABLE_PF                11
131 131
 #define OPENVPN_PLUGIN_ROUTE_PREDOWN            12
132 132
 #define OPENVPN_PLUGIN_CLIENT_CONNECT_DEFER     13
133
-#define OPENVPN_PLUGIN_N                        14
133
+#define OPENVPN_PLUGIN_CLIENT_CONNECT_DEFER_V2  14
134
+#define OPENVPN_PLUGIN_N                        15
134 135
 
135 136
 /*
136 137
  * Build a mask out of a set of plug-in types.
... ...
@@ -2111,36 +2111,48 @@ multi_client_connect_call_plugin_v2(struct multi_context *m,
2111 2111
                                     bool deferred,
2112 2112
                                     unsigned int *option_types_found)
2113 2113
 {
2114
-    if (deferred)
2115
-    {
2116
-        return CC_RET_FAILED;
2117
-    }
2118 2114
     enum client_connect_return ret = CC_RET_SKIPPED;
2119 2115
 #ifdef ENABLE_PLUGIN
2120 2116
     ASSERT(m);
2121 2117
     ASSERT(mi);
2122 2118
     ASSERT(option_types_found);
2123 2119
 
2120
+    int call = deferred ? OPENVPN_PLUGIN_CLIENT_CONNECT_DEFER_V2 :
2121
+               OPENVPN_PLUGIN_CLIENT_CONNECT_V2;
2124 2122
     /* V2 callback, use a plugin_return struct for passing back return info */
2125
-    if (plugin_defined(mi->context.plugins, OPENVPN_PLUGIN_CLIENT_CONNECT_V2))
2123
+    if (plugin_defined(mi->context.plugins, call))
2126 2124
     {
2127 2125
         struct plugin_return pr;
2128 2126
 
2129 2127
         plugin_return_init(&pr);
2130 2128
 
2131
-        if (plugin_call(mi->context.plugins, OPENVPN_PLUGIN_CLIENT_CONNECT_V2,
2132
-                        NULL, &pr, mi->context.c2.es)
2133
-            != OPENVPN_PLUGIN_FUNC_SUCCESS)
2129
+        int plug_ret = plugin_call(mi->context.plugins, call,
2130
+                                   NULL, &pr, mi->context.c2.es);
2131
+        if (plug_ret == OPENVPN_PLUGIN_FUNC_SUCCESS)
2134 2132
         {
2135
-            msg(M_WARN, "WARNING: client-connect-v2 plugin call failed");
2136
-            ret = CC_RET_FAILED;
2133
+            multi_client_connect_post_plugin(m, mi, &pr, option_types_found);
2134
+            ret = CC_RET_SUCCEEDED;
2135
+        }
2136
+        else if (plug_ret == OPENVPN_PLUGIN_FUNC_DEFERRED)
2137
+        {
2138
+            ret = CC_RET_DEFERRED;
2139
+            if (!(plugin_defined(mi->context.plugins,
2140
+                                 OPENVPN_PLUGIN_CLIENT_CONNECT_DEFER_V2)))
2141
+            {
2142
+                msg(M_WARN, "A plugin that defers from the "
2143
+                    "OPENVPN_PLUGIN_CLIENT_CONNECT_V2 call must also "
2144
+                    "declare support for "
2145
+                    "OPENVPN_PLUGIN_CLIENT_CONNECT_DEFER_V2");
2146
+                ret = CC_RET_FAILED;
2147
+            }
2137 2148
         }
2138 2149
         else
2139 2150
         {
2140
-            multi_client_connect_post_plugin(m, mi, &pr, option_types_found);
2141
-            ret = CC_RET_SUCCEEDED;
2151
+            msg(M_WARN, "WARNING: client-connect-v2 plugin call failed");
2152
+            ret = CC_RET_FAILED;
2142 2153
         }
2143 2154
 
2155
+
2144 2156
         plugin_return_free(&pr);
2145 2157
     }
2146 2158
 #endif /* ifdef ENABLE_PLUGIN */
... ...
@@ -107,6 +107,9 @@ plugin_type_name(const int type)
107 107
         case OPENVPN_PLUGIN_CLIENT_CONNECT_DEFER:
108 108
             return "PLUGIN_CLIENT_CONNECT_DEFER";
109 109
 
110
+        case OPENVPN_PLUGIN_CLIENT_CONNECT_DEFER_V2:
111
+            return "PLUGIN_CLIENT_CONNECT_DEFER_V2";
112
+
110 113
         case OPENVPN_PLUGIN_CLIENT_DISCONNECT:
111 114
             return "PLUGIN_CLIENT_DISCONNECT";
112 115