@@ -135,6 +135,7 @@ static int mag_auth(request_rec *req)
135135 char * auth_header_value ;
136136 int ret = HTTP_UNAUTHORIZED ;
137137 gss_ctx_id_t ctx = GSS_C_NO_CONTEXT ;
138+ gss_ctx_id_t * pctx ;
138139 gss_buffer_desc input = GSS_C_EMPTY_BUFFER ;
139140 gss_buffer_desc output = GSS_C_EMPTY_BUFFER ;
140141 gss_buffer_desc name = GSS_C_EMPTY_BUFFER ;
@@ -179,9 +180,10 @@ static int mag_auth(request_rec *req)
179180 req -> user = apr_pstrdup (req -> pool , mc -> user_name );
180181 ret = OK ;
181182 goto done ;
182- } else {
183- ctx = mc -> ctx ;
184183 }
184+ pctx = & mc -> ctx ;
185+ } else {
186+ pctx = & ctx ;
185187 }
186188
187189 auth_header = apr_table_get (req -> headers_in , "Authorization" );
@@ -199,7 +201,7 @@ static int mag_auth(request_rec *req)
199201 if (!input .value ) goto done ;
200202 input .length = apr_base64_decode (input .value , auth_header_value );
201203
202- maj = gss_accept_sec_context (& min , & ctx , GSS_C_NO_CREDENTIAL ,
204+ maj = gss_accept_sec_context (& min , pctx , GSS_C_NO_CREDENTIAL ,
203205 & input , GSS_C_NO_CHANNEL_BINDINGS ,
204206 & client , & mech_type , & output , & flags , NULL ,
205207 & delegated_cred );
@@ -210,12 +212,22 @@ static int mag_auth(request_rec *req)
210212 goto done ;
211213 }
212214
213- if (mc ) {
214- mc -> ctx = ctx ;
215- ctx = GSS_C_NO_CONTEXT ;
215+ if (maj == GSS_S_CONTINUE_NEEDED ) {
216+ if (!cfg -> gss_conn_ctx ) {
217+ ap_log_rerror (APLOG_MARK , APLOG_ERR |APLOG_NOERRNO , 0 , req ,
218+ "Mechanism needs continuation but "
219+ "GSSConnectionContext is off." );
220+ gss_delete_sec_context (& min , pctx , GSS_C_NO_BUFFER );
221+ gss_release_buffer (& min , & output );
222+ output .length = 0 ;
223+ }
224+ goto done ;
216225 }
217226
218- if (maj == GSS_S_CONTINUE_NEEDED ) goto done ;
227+ /* once the connection has been accepted we do not need the context
228+ * anymore, discard it. FIXME: we also need a destructor for those
229+ * mechanisms (like NTLMSSP) that do not complete in one step */
230+ gss_delete_sec_context (& min , pctx , GSS_C_NO_BUFFER );
219231
220232#ifdef HAVE_GSS_STORE_CRED_INTO
221233 if (cfg -> cred_store && delegated_cred != GSS_C_NO_CREDENTIAL ) {
@@ -280,7 +292,6 @@ static int mag_auth(request_rec *req)
280292 gss_release_buffer (& min , & output );
281293 gss_release_name (& min , & client );
282294 gss_release_buffer (& min , & name );
283- gss_delete_sec_context (& min , & ctx , GSS_C_NO_BUFFER );
284295 gss_release_buffer (& min , & lname );
285296 return ret ;
286297}
0 commit comments