1 
2 /* Generic SASL plugin utility functions
3  * Rob Siemborski
4  */
5 /*
6  * Copyright (c) 1998-2016 Carnegie Mellon University.  All rights reserved.
7  *
8  * Redistribution and use in source and binary forms, with or without
9  * modification, are permitted provided that the following conditions
10  * are met:
11  *
12  * 1. Redistributions of source code must retain the above copyright
13  *    notice, this list of conditions and the following disclaimer.
14  *
15  * 2. Redistributions in binary form must reproduce the above copyright
16  *    notice, this list of conditions and the following disclaimer in
17  *    the documentation and/or other materials provided with the
18  *    distribution.
19  *
20  * 3. The name "Carnegie Mellon University" must not be used to
21  *    endorse or promote products derived from this software without
22  *    prior written permission. For permission or any other legal
23  *    details, please contact
24  *      Carnegie Mellon University
25  *      Center for Technology Transfer and Enterprise Creation
26  *      4615 Forbes Avenue
27  *      Suite 302
28  *      Pittsburgh, PA  15213
29  *      (412) 268-7393, fax: (412) 268-7395
30  *      innovation@andrew.cmu.edu
31  *
32  * 4. Redistributions of any form whatsoever must retain the following
33  *    acknowledgment:
34  *    "This product includes software developed by Computing Services
35  *     at Carnegie Mellon University (http://www.cmu.edu/computing/)."
36  *
37  * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO
38  * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
39  * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE
40  * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
41  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN
42  * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
43  * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
44  */
45 
46 #ifndef _PLUGIN_COMMON_H_
47 #define _PLUGIN_COMMON_H_
48 
49 #include <config.h>
50 
51 #ifndef macintosh
52 #ifdef WIN32
53 # include <winsock2.h>
54 #else
55 # include <sys/socket.h>
56 # include <netinet/in.h>
57 # include <arpa/inet.h>
58 # include <netdb.h>
59 #endif /* WIN32 */
60 #endif /* macintosh */
61 
62 #include <sasl.h>
63 #include <saslutil.h>
64 #include <saslplug.h>
65 
66 #ifdef WIN32
67 #define PLUG_API __declspec(dllexport)
68 #else
69 #define PLUG_API extern
70 #endif
71 
72 #define SASL_CLIENT_PLUG_INIT( x ) \
73 extern sasl_client_plug_init_t x##_client_plug_init; \
74 PLUG_API int sasl_client_plug_init(const sasl_utils_t *utils, \
75                          int maxversion, int *out_version, \
76 			 sasl_client_plug_t **pluglist, \
77                          int *plugcount) { \
78         return x##_client_plug_init(utils, maxversion, out_version, \
79 				     pluglist, plugcount); \
80 }
81 
82 #define SASL_SERVER_PLUG_INIT( x ) \
83 extern sasl_server_plug_init_t x##_server_plug_init; \
84 PLUG_API int sasl_server_plug_init(const sasl_utils_t *utils, \
85                          int maxversion, int *out_version, \
86 			 sasl_server_plug_t **pluglist, \
87                          int *plugcount) { \
88         return x##_server_plug_init(utils, maxversion, out_version, \
89 				     pluglist, plugcount); \
90 }
91 
92 #define SASL_AUXPROP_PLUG_INIT( x ) \
93 extern sasl_auxprop_init_t x##_auxprop_plug_init; \
94 PLUG_API int sasl_auxprop_plug_init(const sasl_utils_t *utils, \
95                            int maxversion, int *out_version, \
96                            sasl_auxprop_plug_t **plug, \
97                            const char *plugname) {\
98         return x##_auxprop_plug_init(utils, maxversion, out_version, \
99                                      plug, plugname); \
100 }
101 
102 #define SASL_CANONUSER_PLUG_INIT( x ) \
103 extern sasl_canonuser_init_t x##_canonuser_plug_init; \
104 PLUG_API int sasl_canonuser_init(const sasl_utils_t *utils, \
105                            int maxversion, int *out_version, \
106                            sasl_canonuser_plug_t **plug, \
107                            const char *plugname) {\
108         return x##_canonuser_plug_init(utils, maxversion, out_version, \
109                                      plug, plugname); \
110 }
111 
112 /* note: msg cannot include additional variables, so if you want to
113  * do a printf-format string, then you need to call seterror yourself */
114 #define SETERROR( utils, msg ) (utils)->seterror( (utils)->conn, 0, (msg) )
115 
116 #ifndef MEMERROR
117 #define MEMERROR( utils ) \
118     (utils)->seterror( (utils)->conn, 0, \
119                        "Out of Memory in " __FILE__ " near line %d", __LINE__ )
120 #endif
121 
122 #ifndef PARAMERROR
123 #define PARAMERROR( utils ) \
124     (utils)->seterror( (utils)->conn, 0, \
125                        "Parameter Error in " __FILE__ " near line %d", __LINE__ )
126 #endif
127 
128 #ifndef SASLINT_H
129 typedef struct buffer_info
130 {
131     char *data;
132     unsigned curlen;   /* Current length of data in buffer */
133     unsigned reallen;  /* total length of buffer (>= curlen) */
134 } buffer_info_t;
135 
136 #ifndef HAVE_GETHOSTNAME
137 #ifdef sun
138 /* gotta define gethostname ourselves on suns */
139 extern int gethostname(char *, int);
140 #endif
141 #endif /* HAVE_GETHOSTNAME */
142 
143 #endif /* SASLINT_H */
144 
145 #ifdef __cplusplus
146 extern "C" {
147 #endif
148 
149 int _plug_ipfromstring(const sasl_utils_t *utils, const char *addr,
150 		       struct sockaddr *out, socklen_t outlen);
151 int _plug_iovec_to_buf(const sasl_utils_t *utils, const struct iovec *vec,
152 		       unsigned numiov, buffer_info_t **output);
153 int _plug_buf_alloc(const sasl_utils_t *utils, char **rwbuf,
154 		    unsigned *curlen, unsigned newlen);
155 int _plug_strdup(const sasl_utils_t * utils, const char *in,
156 	         char **out, int *outlen);
157 void _plug_free_string(const sasl_utils_t *utils, char **str);
158 void _plug_free_secret(const sasl_utils_t *utils, sasl_secret_t **secret);
159 
160 #define _plug_get_userid(utils, result, prompt_need) \
161 	_plug_get_simple(utils, SASL_CB_USER, 0, result, prompt_need)
162 #define _plug_get_authid(utils, result, prompt_need) \
163 	_plug_get_simple(utils, SASL_CB_AUTHNAME, 1, result, prompt_need)
164 int _plug_get_simple(const sasl_utils_t *utils, unsigned int id, int required,
165 		     const char **result, sasl_interact_t **prompt_need);
166 
167 int _plug_get_password(const sasl_utils_t *utils, sasl_secret_t **secret,
168 		       unsigned int *iscopy, sasl_interact_t **prompt_need);
169 
170 int _plug_challenge_prompt(const sasl_utils_t *utils, unsigned int id,
171 			   const char *challenge, const char *promptstr,
172 			   const char **result, sasl_interact_t **prompt_need);
173 
174 int _plug_get_realm(const sasl_utils_t *utils, const char **availrealms,
175 		    const char **realm, sasl_interact_t **prompt_need);
176 
177 int _plug_make_prompts(const sasl_utils_t *utils,
178 		       sasl_interact_t **prompts_res,
179 		       const char *user_prompt, const char *user_def,
180 		       const char *auth_prompt, const char *auth_def,
181 		       const char *pass_prompt, const char *pass_def,
182 		       const char *echo_chal,
183 		       const char *echo_prompt, const char *echo_def,
184 		       const char *realm_chal,
185 		       const char *realm_prompt, const char *realm_def);
186 
187 typedef struct decode_context {
188     const sasl_utils_t *utils;
189     unsigned int needsize;	/* How much of the 4-byte size do we need? */
190     char sizebuf[4];		/* Buffer to accumulate the 4-byte size */
191     unsigned int size;		/* Absolute size of the encoded packet */
192     char *buffer;		/* Buffer to accumulate an encoded packet */
193     unsigned int cursize;	/* Amount of packet data in the buffer */
194     unsigned int in_maxbuf;	/* Maximum allowed size of an incoming encoded packet */
195 } decode_context_t;
196 
197 void _plug_decode_init(decode_context_t *text,
198 		       const sasl_utils_t *utils, unsigned int in_maxbuf);
199 
200 int _plug_decode(decode_context_t *text,
201 		 const char *input, unsigned inputlen,
202 		 char **output, unsigned *outputsize, unsigned *outputlen,
203 		 int (*decode_pkt)(void *rock,
204 				   const char *input, unsigned inputlen,
205 				   char **output, unsigned *outputlen),
206 		 void *rock);
207 
208 void _plug_decode_free(decode_context_t *text);
209 
210 int _plug_parseuser(const sasl_utils_t *utils,
211 		    char **user, char **realm, const char *user_realm,
212 		    const char *serverFQDN, const char *input);
213 
214 int _plug_make_fulluser(const sasl_utils_t *utils,
215 			char **fulluser, const char * useronly, const char *realm);
216 
217 char * _plug_get_error_message (const sasl_utils_t *utils,
218 #ifdef WIN32
219 				DWORD error
220 #else
221 				int error
222 #endif
223 				);
224 void _plug_snprintf_os_info (char * osbuf, int osbuf_len);
225 
226 #ifdef __cplusplus
227 }
228 #endif
229 
230 #endif /* _PLUGIN_COMMON_H_ */
231