]> git.ipfire.org Git - thirdparty/openvpn.git/commitdiff
When I began testing OpenVPN v2.1_rc9 I was having trouble authenticating to the...
authorDaniel Johnson <Progman2000@usa.net>
Tue, 30 Mar 2010 13:54:44 +0000 (15:54 +0200)
committerDavid Sommerseth <dazo@users.sourceforge.net>
Thu, 21 Oct 2010 09:35:08 +0000 (11:35 +0200)
plugin /opt/openvpn/openvpn-auth-pam.so
                   "openvpn login OURDOMAIN+USERNAME password PASSWORD"

Finally I turned on more verbose logging and found that the plugin did
not recognize "USERNAME" as something to replace, because it expected
the string to be surrounded by whitespace.  I wrote the following patch
to correct this.  I hope you find it useful,

Signed-off-by: David Sommerseth <dazo@users.sourceforge.net>
plugin/auth-pam/auth-pam.c

index 1d811be001d091347dc171199de912060737709a..5a8e269acd6deb5f9793da828d8c38de2d55dd55 100644 (file)
@@ -111,6 +111,35 @@ struct user_pass {
 /* Background process function */
 static void pam_server (int fd, const char *service, int verb, const struct name_value_list *name_value_list);
 
+/*  Read 'tosearch', replace all occurences of 'searchfor' with 'replacewith' and return
+ *  a pointer to the NEW string.  Does not modify the input strings.  Will not enter an
+ *  infinite loop with clever 'searchfor' and 'replacewith' strings.
+ *  Daniel Johnson - Progman2000@usa.net / djohnson@progman.us
+ */
+static char *
+searchandreplace(const char *tosearch, const char *searchfor, const char *replacewith)
+{
+  if (!tosearch || !searchfor || !replacewith) return 0;
+  if (!strlen(tosearch) || !strlen(searchfor) || !strlen(replacewith)) return 0;
+
+  const char *searching=tosearch;
+  char *scratch;
+  char temp[strlen(tosearch)*10];
+  temp[0]=0;
+
+  scratch = strstr(searching,searchfor);
+  if (!scratch) return strdup(tosearch);
+
+  while (scratch) {
+    strncat(temp,searching,scratch-searching);
+    strcat(temp,replacewith);
+
+    searching=scratch+strlen(searchfor);
+    scratch = strstr(searching,searchfor);
+  }
+  return strdup(temp);
+}
+
 /*
  * Given an environmental variable name, search
  * the envp array for its value, returning it
@@ -551,7 +580,7 @@ my_conv (int n, const struct pam_message **msg_array,
              if (name_value_match (msg->msg, match_name))
                {
                  /* found name/value match */
-                 const char *return_value = NULL;
+                 aresp[i].resp = NULL;
 
                  if (DEBUG (up->verb))
                    fprintf (stderr, "AUTH-PAM: BACKGROUND: name match found, query/match-string ['%s', '%s'] = '%s'\n",
@@ -559,14 +588,13 @@ my_conv (int n, const struct pam_message **msg_array,
                             match_name,
                             match_value);
 
-                 if (!strcmp (match_value, "USERNAME"))
-                   return_value = up->username;
-                 else if (!strcmp (match_value, "PASSWORD"))
-                   return_value = up->password;
+                 if (strstr(match_value, "USERNAME"))
+                   aresp[i].resp = searchandreplace(match_value, "USERNAME", up->username);
+                 else if (strstr(match_value, "PASSWORD"))
+                   aresp[i].resp = searchandreplace(match_value, "PASSWORD", up->password);
                  else
-                   return_value = match_value;
+                   aresp[i].resp = strdup (match_value);
 
-                 aresp[i].resp = strdup (return_value);
                  if (aresp[i].resp == NULL)
                    ret = PAM_CONV_ERR;
                  break;