mirror of https://github.com/lianthony/NT4.0
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
206 lines
4.7 KiB
206 lines
4.7 KiB
/* htspm.c -- Security Protocol Module interface. */
|
|
/* Jeff Hostetler, Spyglass, Inc. 1994. */
|
|
|
|
#include "all.h"
|
|
|
|
|
|
/*********************************************************************
|
|
*
|
|
* HTSPM_SelectProtocol() -- Examine server response for a security
|
|
* protocol that we support. We consider
|
|
* the headers in the order given by the
|
|
* server response.
|
|
*
|
|
*/
|
|
HTSPM * HTSPM_SelectProtocol(int ht_status,
|
|
HTHeader * hServerResponse,
|
|
HTHeaderList ** phlProtocol)
|
|
{
|
|
HTHeaderList * hl;
|
|
|
|
if (ht_status < 0)
|
|
ht_status = - ht_status;
|
|
|
|
if (!hServerResponse)
|
|
{
|
|
return NULL;
|
|
}
|
|
|
|
for (hl=hServerResponse->first; hl; hl=hl->next)
|
|
{
|
|
HTSPM * htspm;
|
|
|
|
htspm = HTSPM_FindProtocol(hl);
|
|
if (htspm)
|
|
{
|
|
XX_DMsg(DBG_SPM,("HTSPM_SelectProtocol: Selected [%s].\n",htspm->szProtocolName));
|
|
|
|
if (phlProtocol)
|
|
*phlProtocol = hl;
|
|
return htspm;
|
|
}
|
|
}
|
|
|
|
/* Fall thru when we cannot find a supported protocol
|
|
(or the server fails to specify one). */
|
|
|
|
if (ht_status == 401)
|
|
ERR_SimpleError(NULL, errSpecify,RES_STRING_SPM11);
|
|
else if (ht_status == 402)
|
|
ERR_SimpleError(NULL, errSpecify,RES_STRING_SPM12);
|
|
|
|
return NULL;
|
|
}
|
|
|
|
|
|
/****************************************************************/
|
|
/****************************************************************/
|
|
/** protocol id list -- allows an spm to register a server **/
|
|
/** response header that it would knows **/
|
|
/** how to service. **/
|
|
/****************************************************************/
|
|
/****************************************************************/
|
|
|
|
typedef struct _PIDL PIDL;
|
|
|
|
struct _PIDL
|
|
{
|
|
PIDL * next;
|
|
|
|
HTSPM * htspm;
|
|
|
|
unsigned char * szIdentHeader; /* 200/401/402 header to branch on (provided by SPM) */
|
|
unsigned char * szIdentValue; /* 200/401/402 value on header to branch on (provided by SPM) */
|
|
unsigned char * szIdentSubValue; /* 200/401/402 sub-value on header to branch on (provided by SPM) */
|
|
};
|
|
|
|
static PIDL * pidlMaster = NULL;
|
|
static PIDL * pidlLast = NULL;
|
|
|
|
|
|
|
|
UI_StatusCode HTSPM_RegisterProtocol(UI_ProtocolId * pi)
|
|
{
|
|
PIDL * pidlNew;
|
|
|
|
XX_DMsg(DBG_SPM,("HTSPM_RegisterProtocol: [%s] '%s' '%s' '%s'.\n",
|
|
pi->htspm->szProtocolName,
|
|
pi->szIdentHeader,
|
|
pi->szIdentValue,
|
|
pi->szIdentSubValue));
|
|
|
|
pidlNew = GTR_CALLOC(1,sizeof(PIDL));
|
|
if (!pidlNew)
|
|
return UI_SC_ERROR_NO_MEMORY;
|
|
|
|
pidlNew->htspm = pi->htspm;
|
|
|
|
pidlNew->szIdentHeader = GTR_MALLOC(strlen(pi->szIdentHeader)+1);
|
|
if (!pidlNew->szIdentHeader)
|
|
goto Fail;
|
|
strcpy(pidlNew->szIdentHeader,pi->szIdentHeader);
|
|
|
|
if (pi->szIdentValue) /* presence of value is optional */
|
|
{
|
|
pidlNew->szIdentValue = GTR_MALLOC(strlen(pi->szIdentValue)+1);
|
|
if (!pidlNew->szIdentValue)
|
|
goto Fail;
|
|
strcpy(pidlNew->szIdentValue,pi->szIdentValue);
|
|
|
|
if (pi->szIdentSubValue) /* presence of sub-value is optional */
|
|
{
|
|
pidlNew->szIdentSubValue = GTR_MALLOC(strlen(pi->szIdentSubValue)+1);
|
|
if (!pidlNew->szIdentSubValue)
|
|
goto Fail;
|
|
strcpy(pidlNew->szIdentSubValue,pi->szIdentSubValue);
|
|
|
|
}
|
|
}
|
|
|
|
pidlNew->next = NULL;
|
|
|
|
if (pidlLast)
|
|
pidlLast->next = pidlNew;
|
|
pidlLast = pidlNew;
|
|
|
|
if (!pidlMaster)
|
|
pidlMaster = pidlNew;
|
|
|
|
return UI_SC_STATUS_OK;
|
|
|
|
|
|
Fail:
|
|
if (pidlNew)
|
|
{
|
|
if (pidlNew->szIdentHeader)
|
|
GTR_FREE(pidlNew->szIdentHeader);
|
|
if (pidlNew->szIdentValue)
|
|
GTR_FREE(pidlNew->szIdentValue);
|
|
if (pidlNew->szIdentSubValue)
|
|
GTR_FREE(pidlNew->szIdentSubValue);
|
|
GTR_FREE(pidlNew);
|
|
}
|
|
|
|
return UI_SC_ERROR_NO_MEMORY;
|
|
}
|
|
|
|
|
|
HTSPM * HTSPM_FindProtocol(HTHeaderList * hl)
|
|
{
|
|
PIDL * pidl;
|
|
|
|
/* with given header line, search our registered protocols list
|
|
* for a match. we match using:
|
|
*
|
|
* header [value [sub-value]]
|
|
*
|
|
*/
|
|
|
|
for (pidl=pidlMaster; pidl; pidl=pidl->next)
|
|
{
|
|
if (strcasecomp(pidl->szIdentHeader,hl->name)==0)
|
|
{
|
|
if (!pidl->szIdentValue)
|
|
return pidl->htspm;
|
|
|
|
if ( (hl->value)
|
|
&& (strcasecomp(pidl->szIdentValue,hl->value)==0))
|
|
{
|
|
if (!pidl->szIdentSubValue)
|
|
return pidl->htspm;
|
|
|
|
if ( (hl->sub_value)
|
|
&& (hl->sub_value->name)
|
|
&& (strcasecomp(pidl->szIdentSubValue,hl->sub_value->name)==0))
|
|
return pidl->htspm;
|
|
}
|
|
}
|
|
}
|
|
|
|
return NULL;
|
|
}
|
|
|
|
void HTSPM_UnRegisterAllProtocols(void)
|
|
{
|
|
PIDL * pidlTemp;
|
|
|
|
while (pidlMaster)
|
|
{
|
|
pidlTemp = pidlMaster->next;
|
|
|
|
if (pidlMaster->szIdentHeader)
|
|
GTR_FREE(pidlMaster->szIdentHeader);
|
|
if (pidlMaster->szIdentValue)
|
|
GTR_FREE(pidlMaster->szIdentValue);
|
|
if (pidlMaster->szIdentSubValue)
|
|
GTR_FREE(pidlMaster->szIdentSubValue);
|
|
|
|
/* we did not malloc htspm */
|
|
|
|
GTR_FREE(pidlMaster);
|
|
pidlMaster = pidlTemp;
|
|
}
|
|
|
|
pidlLast = NULL;
|
|
return;
|
|
}
|