1 /* server.c --- SASL mechanism PLAIN as defined in RFC 2595, server side.
2 * Copyright (C) 2002-2012 Simon Josefsson
4 * This file is part of GNU SASL Library.
6 * GNU SASL Library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public License
8 * as published by the Free Software Foundation; either version 2.1 of
9 * the License, or (at your option) any later version.
11 * GNU SASL Library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with GNU SASL Library; if not, write to the Free
18 * Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
19 * Boston, MA 02110-1301, USA.
27 /* Get specification. */
30 /* Get memcpy, memchr, strlen. */
33 /* Get malloc, free. */
37 _gsasl_plain_server_step (Gsasl_session * sctx,
39 const char *input, size_t input_len,
40 char **output, size_t * output_len)
42 const char *authzidptr = input;
43 char *authidptr = NULL;
44 char *passwordptr = NULL;
45 char *passwdz = NULL, *passprep = NULL, *authidprep = NULL;
52 return GSASL_NEEDS_MORE;
58 authidptr = memchr (input, 0, input_len - 1);
62 passwordptr = memchr (authidptr, 0, input_len - strlen (input) - 1);
66 return GSASL_MECHANISM_PARSE_ERROR;
69 return GSASL_MECHANISM_PARSE_ERROR;
71 /* As the NUL (U+0000) character is used as a deliminator, the NUL
72 (U+0000) character MUST NOT appear in authzid, authcid, or passwd
74 tmplen = input_len - (size_t) (passwordptr - input);
75 if (memchr (passwordptr, 0, tmplen))
76 return GSASL_MECHANISM_PARSE_ERROR;
79 /* Store authid, after preparing it... */
81 res = gsasl_saslprep (authidptr, GSASL_ALLOW_UNASSIGNED,
86 gsasl_property_set (sctx, GSASL_AUTHID, authidprep);
88 /* Store authzid, if absent, use SASLprep(authcid). */
89 if (*authzidptr == '\0')
90 gsasl_property_set (sctx, GSASL_AUTHZID, authidprep);
92 gsasl_property_set (sctx, GSASL_AUTHZID, authzidptr);
97 /* Store passwd, after preparing it... */
99 size_t passwdzlen = input_len - (size_t) (passwordptr - input);
101 /* Need to zero terminate password... */
102 passwdz = malloc (passwdzlen + 1);
104 return GSASL_MALLOC_ERROR;
105 memcpy (passwdz, passwordptr, passwdzlen);
106 passwdz[passwdzlen] = '\0';
108 res = gsasl_saslprep (passwdz, GSASL_ALLOW_UNASSIGNED, &passprep, NULL);
113 gsasl_property_set (sctx, GSASL_PASSWORD, passprep);
116 /* Authorization. Let application verify credentials internally,
117 but fall back to deal with it locally... */
118 res = gsasl_callback (NULL, sctx, GSASL_VALIDATE_SIMPLE);
119 if (res == GSASL_NO_CALLBACK)
124 gsasl_property_set (sctx, GSASL_PASSWORD, NULL);
125 key = gsasl_property_get (sctx, GSASL_PASSWORD);
129 return GSASL_NO_PASSWORD;
132 /* Unassigned code points are not permitted. */
133 res = gsasl_saslprep (key, 0, &normkey, NULL);
140 if (strcmp (normkey, passprep) == 0)
143 res = GSASL_AUTHENTICATION_ERROR;