iceauth.c revision 9ef0b394
1/******************************************************************************
2
3
4Copyright 1993, 1998  The Open Group
5
6Permission to use, copy, modify, distribute, and sell this software and its
7documentation for any purpose is hereby granted without fee, provided that
8the above copyright notice appear in all copies and that both that
9copyright notice and this permission notice appear in supporting
10documentation.
11
12The above copyright notice and this permission notice shall be included in
13all copies or substantial portions of the Software.
14
15THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL THE
18OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
19AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
20CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
21
22Except as contained in this notice, the name of The Open Group shall not be
23used in advertising or otherwise to promote the sale, use or other dealings
24in this Software without prior written authorization from The Open Group.
25
26Author: Ralph Mor, X Consortium
27******************************************************************************/
28
29#ifdef HAVE_CONFIG_H
30#include <config.h>
31#endif
32#include <X11/ICE/ICElib.h>
33#include "ICElibint.h"
34#include <X11/ICE/ICEutil.h>
35
36#include <time.h>
37#define Time_t time_t
38
39static int was_called_state;
40
41/*
42 * MIT-MAGIC-COOKIE-1 is a sample authentication method implemented by
43 * the SI.  It is not part of standard ICElib.
44 */
45
46
47char *
48IceGenerateMagicCookie (
49	int len
50)
51{
52    char    *auth;
53    long    ldata[2];
54    int	    seed;
55    int	    value;
56    int	    i;
57
58    if ((auth = (char *) malloc (len + 1)) == NULL)
59	return (NULL);
60
61#ifdef ITIMER_REAL
62    {
63	struct timeval  now;
64	X_GETTIMEOFDAY (&now);
65	ldata[0] = now.tv_sec;
66	ldata[1] = now.tv_usec;
67    }
68#else
69    {
70#ifndef __UNIXOS2__
71	long    time ();
72#endif
73	ldata[0] = time ((long *) 0);
74	ldata[1] = getpid ();
75    }
76#endif
77    seed = (ldata[0]) + (ldata[1] << 16);
78    srand (seed);
79    for (i = 0; i < len; i++)
80    {
81	value = rand ();
82	auth[i] = value & 0xff;
83    }
84    auth[len] = '\0';
85
86    return (auth);
87}
88
89
90
91IcePoAuthStatus
92_IcePoMagicCookie1Proc (
93	IceConn		iceConn,
94	IcePointer	*authStatePtr,
95	Bool 		cleanUp,
96	Bool		swap,
97	int     	authDataLen,
98	IcePointer	authData,
99	int 		*replyDataLenRet,
100	IcePointer	*replyDataRet,
101	char    	**errorStringRet
102)
103{
104    if (cleanUp)
105    {
106	/*
107	 * We didn't allocate any state.  We're done.
108	 */
109
110	return (IcePoAuthDoneCleanup);
111    }
112
113    *errorStringRet = NULL;
114
115    if (*authStatePtr == NULL)
116    {
117	/*
118	 * This is the first time we're being called.  Search the
119	 * authentication data for the first occurence of
120	 * MIT-MAGIC-COOKIE-1 that matches iceConn->connection_string.
121	 */
122
123	unsigned short  length;
124	char		*data;
125
126	_IceGetPoAuthData ("ICE", iceConn->connection_string,
127	    "MIT-MAGIC-COOKIE-1", &length, &data);
128
129	if (!data)
130	{
131	    const char *tempstr =
132		"Could not find correct MIT-MAGIC-COOKIE-1 authentication";
133
134	    *errorStringRet = strdup(tempstr);
135
136	    return (IcePoAuthFailed);
137	}
138	else
139	{
140	    *authStatePtr = (IcePointer) &was_called_state;
141
142	    *replyDataLenRet = length;
143	    *replyDataRet = data;
144
145	    return (IcePoAuthHaveReply);
146	}
147    }
148    else
149    {
150	/*
151	 * We should never get here for MIT-MAGIC-COOKIE-1 since it is
152	 * a single pass authentication method.
153	 */
154
155	const char *tempstr =
156	    "MIT-MAGIC-COOKIE-1 authentication internal error";
157
158	*errorStringRet = strdup(tempstr);
159
160	return (IcePoAuthFailed);
161    }
162}
163
164IcePoAuthProc	_IcePoAuthProcs[] = {_IcePoMagicCookie1Proc};
165
166
167IcePaAuthStatus
168_IcePaMagicCookie1Proc (
169	IceConn		iceConn,
170	IcePointer	*authStatePtr,
171	Bool		swap,
172	int     	authDataLen,
173	IcePointer	authData,
174	int 		*replyDataLenRet,
175	IcePointer	*replyDataRet,
176	char    	**errorStringRet
177)
178{
179    *errorStringRet = NULL;
180    *replyDataLenRet = 0;
181    *replyDataRet = NULL;
182
183    if (*authStatePtr == NULL)
184    {
185	/*
186	 * This is the first time we're being called.  We don't have
187	 * any data to pass to the other client.
188	 */
189
190	*authStatePtr = (IcePointer) &was_called_state;
191
192	return (IcePaAuthContinue);
193    }
194    else
195    {
196	/*
197	 * Search the authentication data for the first occurence of
198	 * MIT-MAGIC-COOKIE-1 that matches iceConn->connection_string.
199	 */
200
201	unsigned short  length;
202	char		*data;
203
204	_IceGetPaAuthData ("ICE", iceConn->connection_string,
205	    "MIT-MAGIC-COOKIE-1", &length, &data);
206
207	if (data)
208	{
209	    IcePaAuthStatus stat;
210
211	    if (authDataLen == length &&
212	        memcmp (authData, data, authDataLen) == 0)
213	    {
214		stat = IcePaAuthAccepted;
215	    }
216	    else
217	    {
218		const char *tempstr
219		    = "MIT-MAGIC-COOKIE-1 authentication rejected";
220
221		*errorStringRet = strdup(tempstr);
222
223		stat = IcePaAuthRejected;
224	    }
225
226	    free (data);
227	    return (stat);
228	}
229	else
230	{
231	    /*
232	     * We should never get here because in the ConnectionReply
233	     * we should have passed all the valid methods.  So we should
234	     * always find a valid entry.
235	     */
236
237	    const char *tempstr =
238		"MIT-MAGIC-COOKIE-1 authentication internal error";
239
240	    *errorStringRet = strdup(tempstr);
241
242	    return (IcePaAuthFailed);
243	}
244    }
245}
246
247IcePaAuthProc	_IcePaAuthProcs[] = {_IcePaMagicCookie1Proc};
248