[PATCH 4/6] library: Add reconnected() callback

Kevin Cernekee cernekee at gmail.com
Thu Apr 14 23:06:03 PDT 2016


Currently, library callers can pause the connection and then re-enter the
mainloop later on, reusing the same cookie they obtained during the
initial login.  But they do not have an easy way to tell when the VPN
has successfully reconnected and is able to pass traffic.  This could be
useful for informing the host OS (and/or UI) that the VPN has
transitioned back from Reconnecting->Connected.

A callback is only needed on reconnection, not initial connection, because
for the latter case CSTP is started through the
openconnect_make_cstp_connection() API call before entering the mainloop.

Signed-off-by: Kevin Cernekee <cernekee at gmail.com>
---
 .../src/org/infradead/libopenconnect/LibOpenConnect.java |  1 +
 jni.c                                                    | 16 ++++++++++++++++
 libopenconnect.map.in                                    |  1 +
 library.c                                                |  6 ++++++
 openconnect-internal.h                                   |  1 +
 openconnect.h                                            |  6 ++++++
 ssl.c                                                    |  4 ++++
 7 files changed, 35 insertions(+)

diff --git a/java/src/org/infradead/libopenconnect/LibOpenConnect.java b/java/src/org/infradead/libopenconnect/LibOpenConnect.java
index bf545b5..8dc7452 100644
--- a/java/src/org/infradead/libopenconnect/LibOpenConnect.java
+++ b/java/src/org/infradead/libopenconnect/LibOpenConnect.java
@@ -63,6 +63,7 @@ public abstract class LibOpenConnect {
 	public int onTokenLock() { return 0; }
 	public int onTokenUnlock(String newToken) { return 0; }
 	public void onSetupTun() { }
+	public void onReconnected() { }
 
 	/* create/destroy library instances */
 
diff --git a/jni.c b/jni.c
index bb843a4..b5aa92d 100644
--- a/jni.c
+++ b/jni.c
@@ -309,6 +309,21 @@ static void setup_tun_cb(void *privdata)
 	(*ctx->jenv)->PopLocalFrame(ctx->jenv, NULL);
 }
 
+static void reconnected_cb(void *privdata)
+{
+	struct libctx *ctx = privdata;
+	jmethodID mid;
+
+	if ((*ctx->jenv)->PushLocalFrame(ctx->jenv, 256) < 0)
+		return;
+
+	mid = get_obj_mid(ctx, ctx->jobj, "onReconnected", "()V");
+	if (mid)
+		(*ctx->jenv)->CallVoidMethod(ctx->jenv, ctx->jobj, mid);
+
+	(*ctx->jenv)->PopLocalFrame(ctx->jenv, NULL);
+}
+
 static jobject new_auth_form(struct libctx *ctx, struct oc_auth_form *form)
 {
 	jmethodID mid;
@@ -625,6 +640,7 @@ JNIEXPORT jlong JNICALL Java_org_infradead_libopenconnect_LibOpenConnect_init(
 	openconnect_set_protect_socket_handler(ctx->vpninfo, protect_socket_cb);
 	openconnect_set_stats_handler(ctx->vpninfo, stats_cb);
 	openconnect_set_setup_tun_handler(ctx->vpninfo, setup_tun_cb);
+	openconnect_set_reconnected_handler(ctx->vpninfo, reconnected_cb);
 
 	ctx->cmd_fd = openconnect_setup_cmd_pipe(ctx->vpninfo);
 	if (ctx->cmd_fd < 0)
diff --git a/libopenconnect.map.in b/libopenconnect.map.in
index 7c99c86..887db41 100644
--- a/libopenconnect.map.in
+++ b/libopenconnect.map.in
@@ -42,6 +42,7 @@ OPENCONNECT_5.0 {
 	openconnect_set_protect_socket_handler;
 	openconnect_set_proxy_auth;
 	openconnect_set_reported_os;
+	openconnect_set_reconnect_handler;
 	openconnect_set_reqmtu;
 	openconnect_set_setup_tun_handler;
 	openconnect_set_stats_handler;
diff --git a/library.c b/library.c
index 5c4028b..97be310 100644
--- a/library.c
+++ b/library.c
@@ -786,6 +786,12 @@ void openconnect_set_setup_tun_handler(struct openconnect_info *vpninfo,
 	vpninfo->setup_tun = setup_tun;
 }
 
+void openconnect_set_reconnected_handler(struct openconnect_info *vpninfo,
+				         openconnect_reconnected_vfn reconnected)
+{
+	vpninfo->reconnected = reconnected;
+}
+
 void openconnect_set_stats_handler(struct openconnect_info *vpninfo,
 				   openconnect_stats_vfn stats_handler)
 {
diff --git a/openconnect-internal.h b/openconnect-internal.h
index fa729d2..b339ef6 100644
--- a/openconnect-internal.h
+++ b/openconnect-internal.h
@@ -611,6 +611,7 @@ struct openconnect_info {
 	openconnect_protect_socket_vfn protect_socket;
 	openconnect_getaddrinfo_vfn getaddrinfo_override;
 	openconnect_setup_tun_vfn setup_tun;
+	openconnect_reconnected_vfn reconnected;
 
 	int (*ssl_read)(struct openconnect_info *vpninfo, char *buf, size_t len);
 	int (*ssl_gets)(struct openconnect_info *vpninfo, char *buf, size_t len);
diff --git a/openconnect.h b/openconnect.h
index 23a8fb3..22f7c5e 100644
--- a/openconnect.h
+++ b/openconnect.h
@@ -44,6 +44,7 @@ extern "C" {
  *  - Add openconnect_disable_ipv6().
  *  - Add ip_info->gateway_addr.
  *  - Add openconnect_set_setup_tun_handler().
+ *  - Add openconnect_set_reconnected_handler().
  *
  * API version 5.2 (v7.05; 2015-03-10):
  *  - Add openconnect_set_http_auth(), openconnect_set_protocol().
@@ -615,6 +616,11 @@ typedef void (*openconnect_setup_tun_vfn) (void *privdata);
 void openconnect_set_setup_tun_handler(struct openconnect_info *vpninfo,
 				       openconnect_setup_tun_vfn setup_tun);
 
+/* Callback for indicating that a TCP reconnection succeeded. */
+typedef void (*openconnect_reconnected_vfn) (void *privdata);
+void openconnect_set_reconnected_handler(struct openconnect_info *vpninfo,
+				         openconnect_reconnected_vfn reconnected_fn);
+
 #ifdef __cplusplus
 }
 #endif
diff --git a/ssl.c b/ssl.c
index c82a22e..118fb2d 100644
--- a/ssl.c
+++ b/ssl.c
@@ -1024,6 +1024,10 @@ int ssl_reconnect(struct openconnect_info *vpninfo)
 		if (interval > RECONNECT_INTERVAL_MAX)
 			interval = RECONNECT_INTERVAL_MAX;
 	}
+
 	script_config_tun(vpninfo, "reconnect");
+	if (vpninfo->reconnected)
+		vpninfo->reconnected(vpninfo->cbdata);
+
 	return 0;
 }
-- 
1.9.1




More information about the openconnect-devel mailing list