]> www.infradead.org Git - users/dwmw2/openconnect.git/commitdiff
better heuristic for determining where to fill in a token in GP forms
authorDaniel Lenski <dlenski@gmail.com>
Thu, 9 Apr 2020 00:57:26 +0000 (17:57 -0700)
committerDaniel Lenski <dlenski@gmail.com>
Thu, 9 Apr 2020 01:04:25 +0000 (18:04 -0700)
GlobalProtect's prelogin doesn't give us much information to determine where
a token code might be filled in.

Current behavior:

1. Use the password file in the first form as a token field.
2. Ignores the fact that a second "challenge" form might be coming.

New heuristic:

1. If the label for the password field in the first form has a non-default
   value (not empty or “Password”), then treat that as the token field.
2. Otherwise, assume a second form ("challenge") is coming, and treat the
   password field in the first form as a normal password, then treat the
   password field in the second form as the token field.

Signed-off-by: Daniel Lenski <dlenski@gmail.com>
auth-globalprotect.c

index a4a9b5840c561a36b99fae0d2a1ed822d5bc09f7..2843b1e017349ea0e454cdebde08e16f51ab82d4 100644 (file)
@@ -168,8 +168,14 @@ static int parse_prelogin_xml(struct openconnect_info *vpninfo, xmlNode *xml_nod
 
        /* XX: Some VPNs use a password in the first form, followed by a
         * a token in the second ("challenge") form. Others use only a
-        * token. How can we distinguish these? */
-       if (!can_gen_tokencode(vpninfo, form, opt2))
+        * token. How can we distinguish these?
+        *
+        * Currently using the heuristic that a non-default label for the
+        * password in the first form means we should treat the first
+        * form's password as a token field.
+        */
+       if (!can_gen_tokencode(vpninfo, form, opt2) && !ctx->alt_secret
+           && password_label && strcmp(password_label, "Password"))
                opt2->type = OC_FORM_OPT_TOKEN;
        else
                opt2->type = OC_FORM_OPT_PASSWORD;
@@ -208,6 +214,19 @@ static int challenge_cb(struct openconnect_info *vpninfo, char *prompt, char *in
        opt2->_value = NULL;
        opt->type = OC_FORM_OPT_HIDDEN;
 
+       /* XX: Some VPNs use a password in the first form, followed by a
+        * a token in the second ("challenge") form. Others use only a
+        * token. How can we distinguish these?
+        *
+        * Currently using the heuristic that if the password field in
+        * the preceding form wasn't treated as a token field, treat this
+        * as a token field.
+        */
+       if (!can_gen_tokencode(vpninfo, form, opt2) && opt2->type == OC_FORM_OPT_PASSWORD)
+               opt2->type = OC_FORM_OPT_TOKEN;
+       else
+               opt2->type = OC_FORM_OPT_PASSWORD;
+
        if (    !(form->message = strdup(prompt))
                 || !(form->action = strdup(inputStr))
                 || !(form->auth_id = strdup("_challenge"))