/* This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
/*
 * pkix_pl_ldapdefaultclient.c
 *
 * LDAPDefaultClient Function Definitions
 *
 */

/* We can't decode the length of a message without at least this many bytes */
#define MINIMUM_MSG_LENGTH 5

#include "pkix_pl_ldapdefaultclient.h"

/* --Private-LdapDefaultClient-Message-Building-Functions---------------- */

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_MakeBind
 * DESCRIPTION:
 *
 *  This function creates and encodes a Bind message, using the arena pointed
 *  to by "arena", the version number contained in "versionData", the
 *  LDAPBindAPI pointed to by "bindAPI", and the messageID contained in
 *  "msgNum", and stores a pointer to the encoded string at "pBindMsg".
 *
 *  See pkix_pl_ldaptemplates.c for the ASN.1 description of a Bind message.
 *
 *  This code is not used if the DefaultClient was created with a NULL pointer
 *  supplied for the LDAPBindAPI structure. (Bind and Unbind do not seem to be
 *  expected for anonymous Search requests.)
 *
 * PARAMETERS:
 *  "arena"
 *      The address of the PLArenaPool used in encoding the message. Must be
 *       non-NULL.
 *  "versionData"
 *      The Int32 containing the version number to be encoded in the Bind
 *      message.
 *  "bindAPI"
 *      The address of the LDAPBindAPI to be encoded in the Bind message. Must
 *      be non-NULL.
 *  "msgNum"
 *      The Int32 containing the MessageID to be encoded in the Bind message.
 *  "pBindMsg"
 *      The address at which the encoded Bind message will be stored. Must be
 *      non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in a
 *      non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_MakeBind(
        PLArenaPool *arena,
        PKIX_Int32 versionData,
        LDAPBindAPI *bindAPI,
        PKIX_UInt32 msgNum,
        SECItem **pBindMsg,
        void *plContext)
{
        LDAPMessage msg;
        char version = '\0';
        SECItem *encoded = NULL;
        PKIX_UInt32 len = 0;

        PKIX_ENTER(LDAPDEFAULTCLIENT, "pkix_pl_LdapDefaultClient_MakeBind");
        PKIX_NULLCHECK_TWO(arena, pBindMsg);

        PKIX_PL_NSSCALL(LDAPDEFAULTCLIENT, PORT_Memset,
                (&msg, 0, sizeof (LDAPMessage)));

        version = (char)versionData;

        msg.messageID.type = siUnsignedInteger;
        msg.messageID.data = (void*)&msgNum;
        msg.messageID.len = sizeof (msgNum);

        msg.protocolOp.selector = LDAP_BIND_TYPE;

        msg.protocolOp.op.bindMsg.version.type = siUnsignedInteger;
        msg.protocolOp.op.bindMsg.version.data = (void *)&version;
        msg.protocolOp.op.bindMsg.version.len = sizeof (char);

        /*
         * XXX At present we only know how to handle anonymous requests (no
         * authentication), and we are guessing how to do simple authentication.
         * This section will need to be revised and extended when other
         * authentication is needed.
         */
        if (bindAPI->selector == SIMPLE_AUTH) {
                msg.protocolOp.op.bindMsg.bindName.type = siAsciiString;
                msg.protocolOp.op.bindMsg.bindName.data =
                        (void *)bindAPI->chooser.simple.bindName;
                len = PL_strlen(bindAPI->chooser.simple.bindName);
                msg.protocolOp.op.bindMsg.bindName.len = len;

                msg.protocolOp.op.bindMsg.authentication.type = siAsciiString;
                msg.protocolOp.op.bindMsg.authentication.data =
                        (void *)bindAPI->chooser.simple.authentication;
                len = PL_strlen(bindAPI->chooser.simple.authentication);
                msg.protocolOp.op.bindMsg.authentication.len = len;
        }

        PKIX_PL_NSSCALLRV(LDAPDEFAULTCLIENT, encoded, SEC_ASN1EncodeItem,
                (arena, NULL, (void *)&msg, PKIX_PL_LDAPMessageTemplate));
        if (!encoded) {
                PKIX_ERROR(PKIX_SECASN1ENCODEITEMFAILED);
        }

        *pBindMsg = encoded;
cleanup:

        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_MakeUnbind
 * DESCRIPTION:
 *
 *  This function creates and encodes a Unbind message, using the arena pointed
 *  to by "arena" and the messageID contained in "msgNum", and stores a pointer
 *  to the encoded string at "pUnbindMsg".
 *
 *  See pkix_pl_ldaptemplates.c for the ASN.1 description of an Unbind message.
 *
 *  This code is not used if the DefaultClient was created with a NULL pointer
 *  supplied for the LDAPBindAPI structure. (Bind and Unbind do not seem to be
 *  expected for anonymous Search requests.)
 *
 * PARAMETERS:
 *  "arena"
 *      The address of the PLArenaPool used in encoding the message. Must be
 *       non-NULL.
 *  "msgNum"
 *      The Int32 containing the MessageID to be encoded in the Unbind message.
 *  "pUnbindMsg"
 *      The address at which the encoded Unbind message will be stored. Must
 *      be non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in a
 *      non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_MakeUnbind(
        PLArenaPool *arena,
        PKIX_UInt32 msgNum,
        SECItem **pUnbindMsg,
        void *plContext)
{
        LDAPMessage msg;
        SECItem *encoded = NULL;

        PKIX_ENTER(LDAPDEFAULTCLIENT, "pkix_pl_LdapDefaultClient_MakeUnbind");
        PKIX_NULLCHECK_TWO(arena, pUnbindMsg);

        PKIX_PL_NSSCALL(LDAPDEFAULTCLIENT, PORT_Memset,
                (&msg, 0, sizeof (LDAPMessage)));

        msg.messageID.type = siUnsignedInteger;
        msg.messageID.data = (void*)&msgNum;
        msg.messageID.len = sizeof (msgNum);

        msg.protocolOp.selector = LDAP_UNBIND_TYPE;

        msg.protocolOp.op.unbindMsg.dummy.type = siBuffer;
        msg.protocolOp.op.unbindMsg.dummy.data = NULL;
        msg.protocolOp.op.unbindMsg.dummy.len = 0;

        PKIX_PL_NSSCALLRV(LDAPDEFAULTCLIENT, encoded, SEC_ASN1EncodeItem,
                (arena, NULL, (void *)&msg, PKIX_PL_LDAPMessageTemplate));
        if (!encoded) {
                PKIX_ERROR(PKIX_SECASN1ENCODEITEMFAILED);
        }

        *pUnbindMsg = encoded;
cleanup:

        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_MakeAbandon
 * DESCRIPTION:
 *
 *  This function creates and encodes a Abandon message, using the arena pointed
 *  to by "arena" and the messageID contained in "msgNum", and stores a pointer
 *  to the encoded string at "pAbandonMsg".
 *
 *  See pkix_pl_ldaptemplates.c for the ASN.1 description of an Abandon message.
 *
 * PARAMETERS:
 *  "arena"
 *      The address of the PLArenaPool used in encoding the message. Must be
 *       non-NULL.
 *  "msgNum"
 *      The Int32 containing the MessageID to be encoded in the Abandon message.
 *  "pAbandonMsg"
 *      The address at which the encoded Abandon message will be stored. Must
 *      be non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in a
 *      non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_MakeAbandon(
        PLArenaPool *arena,
        PKIX_UInt32 msgNum,
        SECItem **pAbandonMsg,
        void *plContext)
{
        LDAPMessage msg;
        SECItem *encoded = NULL;

        PKIX_ENTER(LDAPDEFAULTCLIENT, "pkix_pl_LdapDefaultClient_MakeAbandon");
        PKIX_NULLCHECK_TWO(arena, pAbandonMsg);

        PKIX_PL_NSSCALL(LDAPDEFAULTCLIENT, PORT_Memset,
                (&msg, 0, sizeof (LDAPMessage)));

        msg.messageID.type = siUnsignedInteger;
        msg.messageID.data = (void*)&msgNum;
        msg.messageID.len = sizeof (msgNum);

        msg.protocolOp.selector = LDAP_ABANDONREQUEST_TYPE;

        msg.protocolOp.op.abandonRequestMsg.messageID.type = siBuffer;
        msg.protocolOp.op.abandonRequestMsg.messageID.data = (void*)&msgNum;
        msg.protocolOp.op.abandonRequestMsg.messageID.len = sizeof (msgNum);

        PKIX_PL_NSSCALLRV(LDAPDEFAULTCLIENT, encoded, SEC_ASN1EncodeItem,
                (arena, NULL, (void *)&msg, PKIX_PL_LDAPMessageTemplate));
        if (!encoded) {
                PKIX_ERROR(PKIX_SECASN1ENCODEITEMFAILED);
        }

        *pAbandonMsg = encoded;
cleanup:

        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_DecodeBindResponse
 * DESCRIPTION:
 *
 *  This function decodes the encoded data pointed to by "src", using the arena
 *  pointed to by "arena", storing the decoded LDAPMessage at "pBindResponse"
 *  and the decoding status at "pStatus".
 *
 * PARAMETERS:
 *  "arena"
 *      The address of the PLArenaPool to be used in decoding the message. Must
 *      be  non-NULL.
 *  "src"
 *      The address of the SECItem containing the DER- (or BER-)encoded string.
 *       Must be non-NULL.
 *  "pBindResponse"
 *      The address at which the LDAPMessage is stored, if the decoding is
 *      successful (the returned status is SECSuccess). Must be non-NULL.
 *  "pStatus"
 *      The address at which the decoding status is stored. Must be non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in a
 *      non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_DecodeBindResponse(
        PLArenaPool *arena,
        SECItem *src,
        LDAPMessage *pBindResponse,
        SECStatus *pStatus,
        void *plContext)
{
        SECStatus rv = SECFailure;
        LDAPMessage response;

        PKIX_ENTER
                (LDAPDEFAULTCLIENT,
                "pkix_pl_LdapDefaultClient_DecodeBindResponse");
        PKIX_NULLCHECK_FOUR(arena, src, pBindResponse, pStatus);

        PKIX_PL_NSSCALL
                (LDAPDEFAULTCLIENT,
                PORT_Memset,
                (&response, 0, sizeof (LDAPMessage)));

        PKIX_PL_NSSCALLRV(LDAPDEFAULTCLIENT, rv, SEC_ASN1DecodeItem,
            (arena, &response, PKIX_PL_LDAPMessageTemplate, src));

        if (rv == SECSuccess) {
                *pBindResponse = response;
        }

        *pStatus = rv;

        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_VerifyBindResponse
 * DESCRIPTION:
 *
 *  This function verifies that the contents of the message in the rcvbuf of
 *  the LdapDefaultClient object pointed to by "client",  and whose length is
 *  provided by "buflen", is a response to a successful Bind.
 *
 * PARAMETERS:
 *  "client"
 *      The address of the LdapDefaultClient object. Must be non-NULL.
 *  "buflen"
 *      The value of the number of bytes in the receive buffer.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in a
 *      non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_VerifyBindResponse(
        PKIX_PL_LdapDefaultClient *client,
        PKIX_UInt32 bufLen,
        void *plContext)
{
        SECItem decode = {siBuffer, NULL, 0};
        SECStatus rv = SECFailure;
        LDAPMessage msg;
        LDAPBindResponse *ldapBindResponse = &msg.protocolOp.op.bindResponseMsg;

        ldapBindResponse->resultCode.data = NULL;

        PKIX_ENTER
                (LDAPDEFAULTCLIENT,
                "pkix_pl_LdapDefaultClient_VerifyBindResponse");
        PKIX_NULLCHECK_TWO(client, client->rcvBuf);

        decode.data = (unsigned char *)(client->rcvBuf);
        decode.len = bufLen;

        PKIX_CHECK(pkix_pl_LdapDefaultClient_DecodeBindResponse
                (client->arena, &decode, &msg, &rv, plContext),
                PKIX_LDAPDEFAULTCLIENTDECODEBINDRESPONSEFAILED);

        if (rv == SECSuccess) {
                if (*(ldapBindResponse->resultCode.data) == SUCCESS) {
                        client->connectStatus = BOUND;
                } else {
                        PKIX_ERROR(PKIX_BINDREJECTEDBYSERVER);
                }
        } else {
                PKIX_ERROR(PKIX_CANTDECODEBINDRESPONSEFROMSERVER);
        }

cleanup:

        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_RecvCheckComplete
 * DESCRIPTION:
 *
 *  This function determines whether the current response in the
 *  LdapDefaultClient pointed to by "client" is complete, in the sense that all
 *  bytes required to satisfy the message length field in the encoding have been
 *  received. If so, the pointer to input data is updated to reflect the number
 *  of bytes consumed, provided by "bytesProcessed". The state machine flag
 *  pointed to by "pKeepGoing" is updated to indicate whether processing can
 *  continue without further input.
 *
 * PARAMETERS:
 *  "client"
 *      The address of the LdapDefaultClient object. Must be non-NULL.
 *  "bytesProcessed"
 *      The UInt32 value of the number of bytes consumed from the current
 *      buffer.
 *  "pKeepGoing"
 *      The address at which the Boolean state machine flag is stored to
 *      indicate whether processing can continue without further input.
 *      Must be non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in a
 *      non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_RecvCheckComplete(
        PKIX_PL_LdapDefaultClient *client,
        PKIX_UInt32 bytesProcessed,
        PKIX_Boolean *pKeepGoing,
        void *plContext)
{
        PKIX_Boolean complete = PKIX_FALSE;
        SECStatus rv = SECFailure;
        LDAPMessageType messageType = 0;
        LDAPResultCode resultCode = 0;

        PKIX_ENTER
                (LDAPDEFAULTCLIENT,
                "pkix_pl_LdapDefaultClient_RecvCheckComplete");
        PKIX_NULLCHECK_TWO(client, pKeepGoing);

        PKIX_CHECK(pkix_pl_LdapResponse_IsComplete
                (client->currentResponse, &complete, plContext),
                PKIX_LDAPRESPONSEISCOMPLETEFAILED);

        if (complete) {
                PKIX_CHECK(pkix_pl_LdapResponse_Decode
                       (client->arena, client->currentResponse, &rv, plContext),
                        PKIX_LDAPRESPONSEDECODEFAILED);

                if (rv != SECSuccess) {
                        PKIX_ERROR(PKIX_CANTDECODESEARCHRESPONSEFROMSERVER);
                }

                PKIX_CHECK(pkix_pl_LdapResponse_GetMessageType
                        (client->currentResponse, &messageType, plContext),
                        PKIX_LDAPRESPONSEGETMESSAGETYPEFAILED);

                if (messageType == LDAP_SEARCHRESPONSEENTRY_TYPE) {

                        if (client->entriesFound == NULL) {
                                PKIX_CHECK(PKIX_List_Create
                                    (&(client->entriesFound), plContext),
                                    PKIX_LISTCREATEFAILED);
                        }

                        PKIX_CHECK(PKIX_List_AppendItem
                                (client->entriesFound,
                                (PKIX_PL_Object *)client->currentResponse,
                                plContext),
                                PKIX_LISTAPPENDITEMFAILED);

                        PKIX_DECREF(client->currentResponse);

                        /* current receive buffer empty? */
                        if (client->currentBytesAvailable == 0) {
                                client->connectStatus = RECV;
                                *pKeepGoing = PKIX_TRUE;
                        } else {
                                client->connectStatus = RECV_INITIAL;
                                client->currentInPtr = &((char *)
                                    (client->currentInPtr))[bytesProcessed];
                                *pKeepGoing = PKIX_TRUE;
                        }

                } else if (messageType == LDAP_SEARCHRESPONSERESULT_TYPE) {
                        PKIX_CHECK(pkix_pl_LdapResponse_GetResultCode
                                (client->currentResponse,
                                &resultCode,
                                plContext),
                                PKIX_LDAPRESPONSEGETRESULTCODEFAILED);

                        if ((client->entriesFound == NULL) &&
                            ((resultCode == SUCCESS) ||
                            (resultCode == NOSUCHOBJECT))) {
                                PKIX_CHECK(PKIX_List_Create
                                    (&(client->entriesFound), plContext),
                                    PKIX_LISTCREATEFAILED);
                        } else if (resultCode == SUCCESS) {
                                PKIX_CHECK(PKIX_List_SetImmutable
                                    (client->entriesFound, plContext),
                                    PKIX_LISTSETIMMUTABLEFAILED);
                                PKIX_CHECK(PKIX_PL_HashTable_Add
                                    (client->cachePtr,
                                    (PKIX_PL_Object *)client->currentRequest,
                                    (PKIX_PL_Object *)client->entriesFound,
                                    plContext),
                                    PKIX_HASHTABLEADDFAILED);
                        } else {
                            PKIX_ERROR(PKIX_UNEXPECTEDRESULTCODEINRESPONSE);
                        }

                        client->connectStatus = BOUND;
                        *pKeepGoing = PKIX_FALSE;
                        PKIX_DECREF(client->currentResponse);

                } else {
                        PKIX_ERROR(PKIX_SEARCHRESPONSEPACKETOFUNKNOWNTYPE);
                }
        } else {
                client->connectStatus = RECV;
                *pKeepGoing = PKIX_TRUE;
        }

cleanup:
        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/* --Private-LdapDefaultClient-Object-Functions------------------------- */

static PKIX_Error *
pkix_pl_LdapDefaultClient_InitiateRequest(
        PKIX_PL_LdapClient *client,
        LDAPRequestParams *requestParams,
        void **pPollDesc,
        PKIX_List **pResponse,
        void *plContext);

static PKIX_Error *
pkix_pl_LdapDefaultClient_ResumeRequest(
        PKIX_PL_LdapClient *client,
        void **pPollDesc,
        PKIX_List **pResponse,
        void *plContext);

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_CreateHelper
 * DESCRIPTION:
 *
 *  This function creates a new LdapDefaultClient using the Socket pointed to
 *  by "socket", the PRIntervalTime pointed to by "timeout", and the
 *  LDAPBindAPI pointed to by "bindAPI", and stores the result at "pClient".
 *
 *  A value of zero for "timeout" means the LDAPClient will use non-blocking
 *  I/O.
 *
 * PARAMETERS:
 *  "socket"
 *      Address of the Socket to be used for the client. Must be non-NULL.
 *  "bindAPI"
 *      The address of the LDAPBindAPI containing the Bind information to be
 *      encoded in the Bind message.
 *  "pClient"
 *      The address at which the created LdapDefaultClient is to be stored.
 *      Must be non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in
 *      a non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
PKIX_Error *
pkix_pl_LdapDefaultClient_CreateHelper(
        PKIX_PL_Socket *socket,
        LDAPBindAPI *bindAPI,
        PKIX_PL_LdapDefaultClient **pClient,
        void *plContext)
{
        PKIX_PL_HashTable *ht;
        PKIX_PL_LdapDefaultClient *ldapDefaultClient = NULL;
        PKIX_PL_Socket_Callback *callbackList;
        PRFileDesc *fileDesc = NULL;
        PLArenaPool *arena = NULL;

        PKIX_ENTER(LDAPDEFAULTCLIENT, "pkix_pl_LdapDefaultClient_CreateHelper");
        PKIX_NULLCHECK_TWO(socket, pClient);

        PKIX_CHECK(PKIX_PL_Object_Alloc
                    (PKIX_LDAPDEFAULTCLIENT_TYPE,
                    sizeof (PKIX_PL_LdapDefaultClient),
                    (PKIX_PL_Object **)&ldapDefaultClient,
                    plContext),
                    PKIX_COULDNOTCREATELDAPDEFAULTCLIENTOBJECT);

        ldapDefaultClient->vtable.initiateFcn =
                pkix_pl_LdapDefaultClient_InitiateRequest;
        ldapDefaultClient->vtable.resumeFcn =
                pkix_pl_LdapDefaultClient_ResumeRequest;

        PKIX_CHECK(pkix_pl_Socket_GetPRFileDesc
                (socket, &fileDesc, plContext),
                PKIX_SOCKETGETPRFILEDESCFAILED);

        ldapDefaultClient->pollDesc.fd = fileDesc;
        ldapDefaultClient->pollDesc.in_flags = 0;
        ldapDefaultClient->pollDesc.out_flags = 0;

        ldapDefaultClient->bindAPI = bindAPI;

        PKIX_CHECK(PKIX_PL_HashTable_Create
                (LDAP_CACHEBUCKETS, 0, &ht, plContext),
                PKIX_HASHTABLECREATEFAILED);

        ldapDefaultClient->cachePtr = ht;

        PKIX_CHECK(pkix_pl_Socket_GetCallbackList
                (socket, &callbackList, plContext),
                PKIX_SOCKETGETCALLBACKLISTFAILED);

        ldapDefaultClient->callbackList = callbackList;

        PKIX_INCREF(socket);
        ldapDefaultClient->clientSocket = socket;

        ldapDefaultClient->messageID = 0;

        ldapDefaultClient->bindAPI = bindAPI;

        arena = PORT_NewArena(DER_DEFAULT_CHUNKSIZE);
        if (!arena) {
            PKIX_ERROR_FATAL(PKIX_OUTOFMEMORY);
        }
        ldapDefaultClient->arena = arena;

        ldapDefaultClient->sendBuf = NULL;
        ldapDefaultClient->bytesToWrite = 0;

        PKIX_CHECK(PKIX_PL_Malloc
                (RCVBUFSIZE, &ldapDefaultClient->rcvBuf, plContext),
                PKIX_MALLOCFAILED);
        ldapDefaultClient->capacity = RCVBUFSIZE;

        ldapDefaultClient->bindMsg = NULL;
        ldapDefaultClient->bindMsgLen = 0;

        ldapDefaultClient->entriesFound = NULL;
        ldapDefaultClient->currentRequest = NULL;
        ldapDefaultClient->currentResponse = NULL;

        *pClient = ldapDefaultClient;

cleanup:

        if (PKIX_ERROR_RECEIVED) {
                PKIX_DECREF(ldapDefaultClient);
        }

        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: PKIX_PL_LdapDefaultClient_Create
 * DESCRIPTION:
 *
 *  This function creates a new LdapDefaultClient using the PRNetAddr pointed to
 *  by "sockaddr", the PRIntervalTime pointed to by "timeout", and the
 *  LDAPBindAPI pointed to by "bindAPI", and stores the result at "pClient".
 *
 *  A value of zero for "timeout" means the LDAPClient will use non-blocking
 *  I/O.
 *
 * PARAMETERS:
 *  "sockaddr"
 *      Address of the PRNetAddr to be used for the socket connection. Must be
 *      non-NULL.
 *  "timeout"
 *      The PRIntervalTime to be used in I/O requests for this client.
 *  "bindAPI"
 *      The address of the LDAPBindAPI containing the Bind information to be
 *      encoded in the Bind message.
 *  "pClient"
 *      The address at which the created LdapDefaultClient is to be stored.
 *      Must be non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in
 *      a non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
PKIX_Error *
PKIX_PL_LdapDefaultClient_Create(
        PRNetAddr *sockaddr,
        PRIntervalTime timeout,
        LDAPBindAPI *bindAPI,
        PKIX_PL_LdapDefaultClient **pClient,
        void *plContext)
{
        PRErrorCode status = 0;
        PKIX_PL_Socket *socket = NULL;
        PKIX_PL_LdapDefaultClient *client = NULL;

        PKIX_ENTER(LDAPDEFAULTCLIENT, "PKIX_PL_LdapDefaultClient_Create");
        PKIX_NULLCHECK_TWO(sockaddr, pClient);

        PKIX_CHECK(pkix_pl_Socket_Create
                (PKIX_FALSE, timeout, sockaddr, &status, &socket, plContext),
                PKIX_SOCKETCREATEFAILED);

        PKIX_CHECK(pkix_pl_LdapDefaultClient_CreateHelper
                (socket, bindAPI, &client, plContext),
                PKIX_LDAPDEFAULTCLIENTCREATEHELPERFAILED);

        /* Did Socket_Create say the connection was made? */
        if (status == 0) {
                if (client->bindAPI != NULL) {
                        client->connectStatus = CONNECTED;
                } else {
                        client->connectStatus = BOUND;
                }
        } else {
                client->connectStatus = CONNECT_PENDING;
        }

        *pClient = client;

cleanup:
        if (PKIX_ERROR_RECEIVED) {
                PKIX_DECREF(client);
        }

        PKIX_DECREF(socket);

        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: PKIX_PL_LdapDefaultClient_CreateByName
 * DESCRIPTION:
 *
 *  This function creates a new LdapDefaultClient using the hostname pointed to
 *  by "hostname", the PRIntervalTime pointed to by "timeout", and the
 *  LDAPBindAPI pointed to by "bindAPI", and stores the result at "pClient".
 *
 *  A value of zero for "timeout" means the LDAPClient will use non-blocking
 *  I/O.
 *
 * PARAMETERS:
 *  "hostname"
 *      Address of the hostname to be used for the socket connection. Must be
 *      non-NULL.
 *  "timeout"
 *      The PRIntervalTime to be used in I/O requests for this client.
 *  "bindAPI"
 *      The address of the LDAPBindAPI containing the Bind information to be
 *      encoded in the Bind message.
 *  "pClient"
 *      The address at which the created LdapDefaultClient is to be stored.
 *      Must be non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in
 *      a non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
PKIX_Error *
PKIX_PL_LdapDefaultClient_CreateByName(
        char *hostname,
        PRIntervalTime timeout,
        LDAPBindAPI *bindAPI,
        PKIX_PL_LdapDefaultClient **pClient,
        void *plContext)
{
        PRErrorCode status = 0;
        PKIX_PL_Socket *socket = NULL;
        PKIX_PL_LdapDefaultClient *client = NULL;

        PKIX_ENTER(LDAPDEFAULTCLIENT, "PKIX_PL_LdapDefaultClient_CreateByName");
        PKIX_NULLCHECK_TWO(hostname, pClient);

        PKIX_CHECK(pkix_pl_Socket_CreateByName
                (PKIX_FALSE, timeout, hostname, &status, &socket, plContext),
                PKIX_SOCKETCREATEBYNAMEFAILED);

        PKIX_CHECK(pkix_pl_LdapDefaultClient_CreateHelper
                (socket, bindAPI, &client, plContext),
                PKIX_LDAPDEFAULTCLIENTCREATEHELPERFAILED);

        /* Did Socket_Create say the connection was made? */
        if (status == 0) {
                if (client->bindAPI != NULL) {
                        client->connectStatus = CONNECTED;
                } else {
                        client->connectStatus = BOUND;
                }
        } else {
                client->connectStatus = CONNECT_PENDING;
        }

        *pClient = client;

cleanup:
        if (PKIX_ERROR_RECEIVED) {
                PKIX_DECREF(client);
        }

        PKIX_DECREF(socket);

        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_Destroy
 * (see comments for PKIX_PL_DestructorCallback in pkix_pl_system.h)
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_Destroy(
        PKIX_PL_Object *object,
        void *plContext)
{
        PKIX_Int32 bytesWritten = 0;
        PKIX_PL_LdapDefaultClient *client = NULL;
        PKIX_PL_Socket_Callback *callbackList = NULL;
        SECItem *encoded = NULL;

        PKIX_ENTER(LDAPDEFAULTCLIENT,
                    "pkix_pl_LdapDefaultClient_Destroy");
        PKIX_NULLCHECK_ONE(object);

        PKIX_CHECK(pkix_CheckType
                    (object, PKIX_LDAPDEFAULTCLIENT_TYPE, plContext),
                    PKIX_OBJECTNOTANLDAPDEFAULTCLIENT);

        client = (PKIX_PL_LdapDefaultClient *)object;

        switch (client->connectStatus) {
        case CONNECT_PENDING:
                break;
        case CONNECTED:
        case BIND_PENDING:
        case BIND_RESPONSE:
        case BIND_RESPONSE_PENDING:
        case BOUND:
        case SEND_PENDING:
        case RECV:
        case RECV_PENDING:
        case RECV_INITIAL:
        case RECV_NONINITIAL:
        case ABANDON_PENDING:
                if (client->bindAPI != NULL) {
                        PKIX_CHECK(pkix_pl_LdapDefaultClient_MakeUnbind
                                (client->arena,
                                ++(client->messageID),
                                &encoded,
                                plContext),
                                PKIX_LDAPDEFAULTCLIENTMAKEUNBINDFAILED);

                        callbackList =
                                (PKIX_PL_Socket_Callback *)(client->callbackList);
                        PKIX_CHECK(callbackList->sendCallback
                                (client->clientSocket,
                                encoded->data,
                                encoded->len,
                                &bytesWritten,
                                plContext),
                                PKIX_SOCKETSENDFAILED);
                }
                break;
        default:
                PKIX_ERROR(PKIX_LDAPDEFAULTCLIENTINILLEGALSTATE);
        }

        PKIX_DECREF(client->cachePtr);
        PKIX_DECREF(client->clientSocket);
        PKIX_DECREF(client->entriesFound);
        PKIX_DECREF(client->currentRequest);
        PKIX_DECREF(client->currentResponse);

        PKIX_CHECK(PKIX_PL_Free
		(client->rcvBuf, plContext), PKIX_FREEFAILED);

        PKIX_PL_NSSCALL
                (LDAPDEFAULTCLIENT,
                PORT_FreeArena,
                (client->arena, PR_FALSE));

cleanup:

        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_Hashcode
 * (see comments for PKIX_PL_HashcodeCallback in pkix_pl_system.h)
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_Hashcode(
        PKIX_PL_Object *object,
        PKIX_UInt32 *pHashcode,
        void *plContext)
{
        PKIX_PL_LdapDefaultClient *ldapDefaultClient = NULL;
        PKIX_UInt32 tempHash = 0;

        PKIX_ENTER
                (LDAPDEFAULTCLIENT, "pkix_pl_LdapDefaultClient_Hashcode");
        PKIX_NULLCHECK_TWO(object, pHashcode);

        PKIX_CHECK(pkix_CheckType
                (object, PKIX_LDAPDEFAULTCLIENT_TYPE, plContext),
                PKIX_OBJECTNOTANLDAPDEFAULTCLIENT);

        ldapDefaultClient = (PKIX_PL_LdapDefaultClient *)object;

        PKIX_CHECK(PKIX_PL_Object_Hashcode
                ((PKIX_PL_Object *)ldapDefaultClient->clientSocket,
                &tempHash,
                plContext),
                PKIX_SOCKETHASHCODEFAILED);

        if (ldapDefaultClient->bindAPI != NULL) {
                tempHash = (tempHash << 7) +
                        ldapDefaultClient->bindAPI->selector;
        }

        *pHashcode = tempHash;

cleanup:

        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_Equals
 * (see comments for PKIX_PL_EqualsCallback in pkix_pl_system.h)
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_Equals(
        PKIX_PL_Object *firstObject,
        PKIX_PL_Object *secondObject,
        PKIX_Int32 *pResult,
        void *plContext)
{
        PKIX_PL_LdapDefaultClient *firstClientContext = NULL;
        PKIX_PL_LdapDefaultClient *secondClientContext = NULL;
        PKIX_Int32 compare = 0;

        PKIX_ENTER(LDAPDEFAULTCLIENT, "pkix_pl_LdapDefaultClient_Equals");
        PKIX_NULLCHECK_THREE(firstObject, secondObject, pResult);

        *pResult = PKIX_FALSE;

        PKIX_CHECK(pkix_CheckTypes
                (firstObject,
                secondObject,
                PKIX_LDAPDEFAULTCLIENT_TYPE,
                plContext),
                PKIX_OBJECTNOTANLDAPDEFAULTCLIENT);

        firstClientContext = (PKIX_PL_LdapDefaultClient *)firstObject;
        secondClientContext = (PKIX_PL_LdapDefaultClient *)secondObject;

        if (firstClientContext == secondClientContext) {
                *pResult = PKIX_TRUE;
                goto cleanup;
        }

        PKIX_CHECK(PKIX_PL_Object_Equals
                ((PKIX_PL_Object *)firstClientContext->clientSocket,
                (PKIX_PL_Object *)secondClientContext->clientSocket,
                &compare,
                plContext),
                PKIX_SOCKETEQUALSFAILED);

        if (!compare) {
                goto cleanup;
        }

        if (PKIX_EXACTLY_ONE_NULL
                (firstClientContext->bindAPI, secondClientContext->bindAPI)) {
                goto cleanup;
        }

        if (firstClientContext->bindAPI) {
                if (firstClientContext->bindAPI->selector !=
                    secondClientContext->bindAPI->selector) {
                        goto cleanup;
                }
        }

        *pResult = PKIX_TRUE;

cleanup:

        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_RegisterSelf
 *
 * DESCRIPTION:
 *  Registers PKIX_PL_LDAPDEFAULTCLIENT_TYPE and its related
 *  functions with systemClasses[]
 *
 * THREAD SAFETY:
 *  Not Thread Safe - for performance and complexity reasons
 *
 *  Since this function is only called by PKIX_PL_Initialize, which should
 *  only be called once, it is acceptable that this function is not
 *  thread-safe.
 */
PKIX_Error *
pkix_pl_LdapDefaultClient_RegisterSelf(void *plContext)
{
        extern pkix_ClassTable_Entry systemClasses[PKIX_NUMTYPES];
        pkix_ClassTable_Entry entry;

        PKIX_ENTER
                (LDAPDEFAULTCLIENT,
                "pkix_pl_LdapDefaultClient_RegisterSelf");

        entry.description = "LdapDefaultClient";
        entry.objCounter = 0;
        entry.typeObjectSize = sizeof(PKIX_PL_LdapDefaultClient);
        entry.destructor = pkix_pl_LdapDefaultClient_Destroy;
        entry.equalsFunction = pkix_pl_LdapDefaultClient_Equals;
        entry.hashcodeFunction = pkix_pl_LdapDefaultClient_Hashcode;
        entry.toStringFunction = NULL;
        entry.comparator = NULL;
        entry.duplicateFunction = NULL;

        systemClasses[PKIX_LDAPDEFAULTCLIENT_TYPE] = entry;

        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_GetPollDesc
 * DESCRIPTION:
 *
 *  This function retrieves the PRPollDesc from the LdapDefaultClient
 *  pointed to by "context" and stores the address at "pPollDesc".
 *
 * PARAMETERS:
 *  "context"
 *      The LdapDefaultClient whose PRPollDesc is desired. Must be non-NULL.
 *  "pPollDesc"
 *      Address where PRPollDesc will be stored. Must be non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
PKIX_Error *
pkix_pl_LdapDefaultClient_GetPollDesc(
        PKIX_PL_LdapDefaultClient *context,
        PRPollDesc **pPollDesc,
        void *plContext)
{
        PKIX_ENTER
                (LDAPDEFAULTCLIENT,
                "pkix_pl_LdapDefaultClient_GetPollDesc");
        PKIX_NULLCHECK_TWO(context, pPollDesc);

        *pPollDesc = &(context->pollDesc);

        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/* --Private-Ldap-CertStore-I/O-Functions---------------------------- */
/*
 * FUNCTION: pkix_pl_LdapDefaultClient_ConnectContinue
 * DESCRIPTION:
 *
 *  This function determines whether a socket Connect initiated earlier for the
 *  CertStore embodied in the LdapDefaultClient "client" has completed, and
 *  stores in "pKeepGoing" a flag indicating whether processing can continue
 *  without further input.
 *
 * PARAMETERS:
 *  "client"
 *      The address of the LdapDefaultClient object. Must be non-NULL.
 *  "pKeepGoing"
 *      The address at which the Boolean state machine flag is stored to
 *      indicate whether processing can continue without further input.
 *      Must be non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in a
 *      non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_ConnectContinue(
        PKIX_PL_LdapDefaultClient *client,
        PKIX_Boolean *pKeepGoing,
        void *plContext)
{
        PKIX_PL_Socket_Callback *callbackList;
        PRErrorCode status;
        PKIX_Boolean keepGoing = PKIX_FALSE;

        PKIX_ENTER
                (LDAPDEFAULTCLIENT,
                "pkix_pl_LdapDefaultClient_ConnectContinue");
        PKIX_NULLCHECK_ONE(client);

        callbackList = (PKIX_PL_Socket_Callback *)(client->callbackList);

        PKIX_CHECK(callbackList->connectcontinueCallback
                (client->clientSocket, &status, plContext),
                PKIX_SOCKETCONNECTCONTINUEFAILED);

        if (status == 0) {
                if (client->bindAPI != NULL) {
                        client->connectStatus = CONNECTED;
                } else {
                        client->connectStatus = BOUND;
                }
                keepGoing = PKIX_FALSE;
        } else if (status != PR_IN_PROGRESS_ERROR) {
                PKIX_ERROR(PKIX_UNEXPECTEDERRORINESTABLISHINGCONNECTION);
        }

        PKIX_CHECK(PKIX_PL_Object_InvalidateCache
                ((PKIX_PL_Object *)client, plContext),
                PKIX_OBJECTINVALIDATECACHEFAILED);

        *pKeepGoing = keepGoing;

cleanup:
        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_Bind
 * DESCRIPTION:
 *
 *  This function creates and sends the LDAP-protocol Bind message for the
 *  CertStore embodied in the LdapDefaultClient "client", and stores in
 *  "pKeepGoing" a flag indicating whether processing can continue without
 *  further input.
 *
 * PARAMETERS:
 *  "client"
 *      The address of the LdapDefaultClient object. Must be non-NULL.
 *  "pKeepGoing"
 *      The address at which the Boolean state machine flag is stored to
 *      indicate whether processing can continue without further input.
 *      Must be non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in a
 *      non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_Bind(
        PKIX_PL_LdapDefaultClient *client,
        PKIX_Boolean *pKeepGoing,
        void *plContext)
{
        SECItem *encoded = NULL;
        PKIX_Int32 bytesWritten = 0;
        PKIX_PL_Socket_Callback *callbackList;

        PKIX_ENTER(LDAPDEFAULTCLIENT, "pkix_pl_LdapDefaultClient_Bind");
        PKIX_NULLCHECK_ONE(client);

        /* if we have not yet constructed the BIND message, build it now */
        if (!(client->bindMsg)) {
                PKIX_CHECK(pkix_pl_LdapDefaultClient_MakeBind
                        (client->arena,
                        3,
                        client->bindAPI,
                        client->messageID,
                        &encoded,
                        plContext),
                        PKIX_LDAPDEFAULTCLIENTMAKEBINDFAILED);
                client->bindMsg = encoded->data;
                client->bindMsgLen = encoded->len;
        }

        callbackList = (PKIX_PL_Socket_Callback *)(client->callbackList);

        PKIX_CHECK(callbackList->sendCallback
                (client->clientSocket,
                client->bindMsg,
                client->bindMsgLen,
                &bytesWritten,
                plContext),
                PKIX_SOCKETSENDFAILED);

        client->lastIO = PR_Now();

        if (bytesWritten < 0) {
                client->connectStatus = BIND_PENDING;
                *pKeepGoing = PKIX_FALSE;
        } else {
                client->connectStatus = BIND_RESPONSE;
                *pKeepGoing = PKIX_TRUE;
        }

        PKIX_CHECK(PKIX_PL_Object_InvalidateCache
                ((PKIX_PL_Object *)client, plContext),
                PKIX_OBJECTINVALIDATECACHEFAILED);

cleanup:
        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_BindContinue
 * DESCRIPTION:
 *
 *  This function determines whether the LDAP-protocol Bind message for the
 *  CertStore embodied in the LdapDefaultClient "client" has completed, and
 *  stores in "pKeepGoing" a flag indicating whether processing can continue
 *  without further input.
 *
 * PARAMETERS:
 *  "client"
 *      The address of the LdapDefaultClient object. Must be non-NULL.
 *  "pKeepGoing"
 *      The address at which the Boolean state machine flag is stored to
 *      indicate whether processing can continue without further input.
 *      Must be non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in a
 *      non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
PKIX_Error *pkix_pl_LdapDefaultClient_BindContinue(
        PKIX_PL_LdapDefaultClient *client,
        PKIX_Boolean *pKeepGoing,
        void *plContext)
{
        PKIX_Int32 bytesWritten = 0;
        PKIX_PL_Socket_Callback *callbackList = NULL;

        PKIX_ENTER(LDAPDEFAULTCLIENT, "pkix_pl_LdapDefaultClient_BindContinue");
        PKIX_NULLCHECK_ONE(client);

        *pKeepGoing = PKIX_FALSE;

        callbackList = (PKIX_PL_Socket_Callback *)(client->callbackList);

        PKIX_CHECK(callbackList->pollCallback
                (client->clientSocket, &bytesWritten, NULL, plContext),
                PKIX_SOCKETPOLLFAILED);

        /*
         * If the send completed we can proceed to try for the
         * response. If the send did not complete we will have
         * continue to poll.
         */
        if (bytesWritten >= 0) {

                client->connectStatus = BIND_RESPONSE;

                PKIX_CHECK(PKIX_PL_Object_InvalidateCache
                        ((PKIX_PL_Object *)client, plContext),
                        PKIX_OBJECTINVALIDATECACHEFAILED);

                *pKeepGoing = PKIX_TRUE;
        }

cleanup:
        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_BindResponse
 * DESCRIPTION:
 *
 *  This function attempts to read the LDAP-protocol BindResponse message for
 *  the CertStore embodied in the LdapDefaultClient "client", and stores in
 *  "pKeepGoing" a flag indicating whether processing can continue without
 *  further input.
 *
 *  If a BindResponse is received with a Result code of 0 (success), we
 *  continue with the connection. If a non-zero Result code is received,
 *  we throw an Error. Some more sophisticated handling of that condition
 *  might be in order in the future.
 *
 * PARAMETERS:
 *  "client"
 *      The address of the LdapDefaultClient object. Must be non-NULL.
 *  "pKeepGoing"
 *      The address at which the Boolean state machine flag is stored to
 *      indicate whether processing can continue without further input.
 *      Must be non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in a
 *      non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_BindResponse(
        PKIX_PL_LdapDefaultClient *client,
        PKIX_Boolean *pKeepGoing,
        void *plContext)
{
        PKIX_Int32 bytesRead = 0;
        PKIX_PL_Socket_Callback *callbackList = NULL;

        PKIX_ENTER(LDAPDEFAULTCLIENT, "pkix_pl_LdapDefaultClient_BindResponse");
        PKIX_NULLCHECK_TWO(client, client->rcvBuf);

        callbackList = (PKIX_PL_Socket_Callback *)(client->callbackList);

        PKIX_CHECK(callbackList->recvCallback
                (client->clientSocket,
                client->rcvBuf,
                client->capacity,
                &bytesRead,
                plContext),
                PKIX_SOCKETRECVFAILED);

        client->lastIO = PR_Now();

        if (bytesRead > 0) {
                PKIX_CHECK(pkix_pl_LdapDefaultClient_VerifyBindResponse
                        (client, bytesRead, plContext),
                        PKIX_LDAPDEFAULTCLIENTVERIFYBINDRESPONSEFAILED);
                /*
                 * XXX What should we do if failure? At present if
                 * VerifyBindResponse throws an Error, we do too.
                 */
                client->connectStatus = BOUND;
        } else {
                client->connectStatus = BIND_RESPONSE_PENDING;
        }

        PKIX_CHECK(PKIX_PL_Object_InvalidateCache
                ((PKIX_PL_Object *)client, plContext),
                PKIX_OBJECTINVALIDATECACHEFAILED);

        *pKeepGoing = PKIX_TRUE;

cleanup:
        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_BindResponseContinue
 * DESCRIPTION:
 *
 *  This function determines whether the LDAP-protocol BindResponse message for
 *  the CertStore embodied in the LdapDefaultClient "client" has completed, and
 *  stores in "pKeepGoing" a flag indicating whether processing can continue
 *  without further input.
 *
 * PARAMETERS:
 *  "client"
 *      The address of the LdapDefaultClient object. Must be non-NULL.
 *  "pKeepGoing"
 *      The address at which the Boolean state machine flag is stored to
 *      indicate whether processing can continue without further input.
 *      Must be non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in a
 *      non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_BindResponseContinue(
        PKIX_PL_LdapDefaultClient *client,
        PKIX_Boolean *pKeepGoing,
        void *plContext)
{
        PKIX_Int32 bytesRead = 0;
        PKIX_PL_Socket_Callback *callbackList = NULL;

        PKIX_ENTER
                (LDAPDEFAULTCLIENT,
                "pkix_pl_LdapDefaultClient_BindResponseContinue");
        PKIX_NULLCHECK_ONE(client);

        callbackList = (PKIX_PL_Socket_Callback *)(client->callbackList);

        PKIX_CHECK(callbackList->pollCallback
                (client->clientSocket, NULL, &bytesRead, plContext),
                PKIX_SOCKETPOLLFAILED);

        if (bytesRead > 0) {
                PKIX_CHECK(pkix_pl_LdapDefaultClient_VerifyBindResponse
                        (client, bytesRead, plContext),
                        PKIX_LDAPDEFAULTCLIENTVERIFYBINDRESPONSEFAILED);
                client->connectStatus = BOUND;

                PKIX_CHECK(PKIX_PL_Object_InvalidateCache
                        ((PKIX_PL_Object *)client, plContext),
                        PKIX_OBJECTINVALIDATECACHEFAILED);

                *pKeepGoing = PKIX_TRUE;
        } else {
                *pKeepGoing = PKIX_FALSE;
        }

cleanup:
        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_Send
 * DESCRIPTION:
 *
 *  This function creates and sends an LDAP-protocol message for the
 *  CertStore embodied in the LdapDefaultClient "client", and stores in
 *  "pKeepGoing" a flag indicating whether processing can continue without
 *  further input, and at "pBytesTransferred" the number of bytes sent.
 *
 *  If "pBytesTransferred" is zero, it indicates that non-blocking I/O is in use
 *  and that transmission has not completed.
 *
 * PARAMETERS:
 *  "client"
 *      The address of the LdapDefaultClient object. Must be non-NULL.
 *  "pKeepGoing"
 *      The address at which the Boolean state machine flag is stored to
 *      indicate whether processing can continue without further input.
 *      Must be non-NULL.
 *  "pBytesTransferred"
 *      The address at which the number of bytes sent is stored. Must be
 *      non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in a
 *      non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_Send(
        PKIX_PL_LdapDefaultClient *client,
        PKIX_Boolean *pKeepGoing,
        PKIX_UInt32 *pBytesTransferred,
        void *plContext)
{
        PKIX_Int32 bytesWritten = 0;
        PKIX_PL_Socket_Callback *callbackList = NULL;

        PKIX_ENTER(LDAPDEFAULTCLIENT, "pkix_pl_LdapDefaultClient_Send");
        PKIX_NULLCHECK_THREE(client, pKeepGoing, pBytesTransferred);

        *pKeepGoing = PKIX_FALSE;

        /* Do we have anything waiting to go? */
        if (client->sendBuf) {
                callbackList = (PKIX_PL_Socket_Callback *)(client->callbackList);

                PKIX_CHECK(callbackList->sendCallback
                        (client->clientSocket,
                        client->sendBuf,
                        client->bytesToWrite,
                        &bytesWritten,
                        plContext),
                        PKIX_SOCKETSENDFAILED);

                client->lastIO = PR_Now();

                /*
                 * If the send completed we can proceed to try for the
                 * response. If the send did not complete we will have
                 * to poll for completion later.
                 */
                if (bytesWritten >= 0) {
                        client->sendBuf = NULL;
                        client->connectStatus = RECV;
                        *pKeepGoing = PKIX_TRUE;

                } else {
                        *pKeepGoing = PKIX_FALSE;
                        client->connectStatus = SEND_PENDING;
                }

        }

        PKIX_CHECK(PKIX_PL_Object_InvalidateCache
                ((PKIX_PL_Object *)client, plContext),
                PKIX_OBJECTINVALIDATECACHEFAILED);

        *pBytesTransferred = bytesWritten;

cleanup:
        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_SendContinue
 * DESCRIPTION:
 *
 *  This function determines whether the sending of the LDAP-protocol message
 *  for the CertStore embodied in the LdapDefaultClient "client" has completed,
 *  and stores in "pKeepGoing" a flag indicating whether processing can continue
 *  without further input, and at "pBytesTransferred" the number of bytes sent.
 *
 *  If "pBytesTransferred" is zero, it indicates that non-blocking I/O is in use
 *  and that transmission has not completed.
 *
 * PARAMETERS:
 *  "client"
 *      The address of the LdapDefaultClient object. Must be non-NULL.
 *  "pKeepGoing"
 *      The address at which the Boolean state machine flag is stored to
 *      indicate whether processing can continue without further input.
 *      Must be non-NULL.
 *  "pBytesTransferred"
 *      The address at which the number of bytes sent is stored. Must be
 *      non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in a
 *      non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_SendContinue(
        PKIX_PL_LdapDefaultClient *client,
        PKIX_Boolean *pKeepGoing,
        PKIX_UInt32 *pBytesTransferred,
        void *plContext)
{
        PKIX_Int32 bytesWritten = 0;
        PKIX_PL_Socket_Callback *callbackList = NULL;

        PKIX_ENTER(LDAPDEFAULTCLIENT, "pkix_pl_LdapDefaultClient_SendContinue");
        PKIX_NULLCHECK_THREE(client, pKeepGoing, pBytesTransferred);

        *pKeepGoing = PKIX_FALSE;

        callbackList = (PKIX_PL_Socket_Callback *)(client->callbackList);

        PKIX_CHECK(callbackList->pollCallback
                (client->clientSocket, &bytesWritten, NULL, plContext),
                PKIX_SOCKETPOLLFAILED);

        /*
         * If the send completed we can proceed to try for the
         * response. If the send did not complete we will have
         * continue to poll.
         */
        if (bytesWritten >= 0) {
                client->sendBuf = NULL;
                client->connectStatus = RECV;

                PKIX_CHECK(PKIX_PL_Object_InvalidateCache
                        ((PKIX_PL_Object *)client, plContext),
                        PKIX_OBJECTINVALIDATECACHEFAILED);

                *pKeepGoing = PKIX_TRUE;
        }

        *pBytesTransferred = bytesWritten;

cleanup:
        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_Recv
 * DESCRIPTION:
 *
 *  This function receives an LDAP-protocol message for the CertStore embodied
 *  in the LdapDefaultClient "client", and stores in "pKeepGoing" a flag
 *  indicating whether processing can continue without further input.
 *
 * PARAMETERS:
 *  "client"
 *      The address of the LdapDefaultClient object. Must be non-NULL.
 *  "pKeepGoing"
 *      The address at which the Boolean state machine flag is stored to
 *      indicate whether processing can continue without further input.
 *      Must be non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in a
 *      non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_Recv(
        PKIX_PL_LdapDefaultClient *client,
        PKIX_Boolean *pKeepGoing,
        void *plContext)
{
        PKIX_Int32 bytesRead = 0;
        PKIX_UInt32 bytesToRead = 0;
        PKIX_PL_Socket_Callback *callbackList = NULL;

        PKIX_ENTER(LDAPDEFAULTCLIENT, "pkix_pl_LdapDefaultClient_Recv");
        PKIX_NULLCHECK_THREE(client, pKeepGoing, client->rcvBuf);

        callbackList = (PKIX_PL_Socket_Callback *)(client->callbackList);

        /*
         * If we attempt to fill our buffer with every read, we increase
         * the risk of an ugly situation: one or two bytes of a new message
         * left over at the end of processing one message. With such a
         * fragment, we can't decode a byte count and so won't know how much
         * space to allocate for the next LdapResponse. We try to avoid that
         * case by reading just enough to complete the current message, unless
         * there will be at least MINIMUM_MSG_LENGTH bytes left over.
         */
        if (client->currentResponse) {
                PKIX_CHECK(pkix_pl_LdapResponse_GetCapacity
                        (client->currentResponse, &bytesToRead, plContext),
                        PKIX_LDAPRESPONSEGETCAPACITYFAILED);
                if ((bytesToRead > client->capacity) ||
                    ((bytesToRead + MINIMUM_MSG_LENGTH) < client->capacity)) {
                        bytesToRead = client->capacity;
                }
        } else {
                bytesToRead = client->capacity;
        }

        client->currentBytesAvailable = 0;

        PKIX_CHECK(callbackList->recvCallback
                (client->clientSocket,
                (void *)client->rcvBuf,
                bytesToRead,
                &bytesRead,
                plContext),
                PKIX_SOCKETRECVFAILED);

        client->currentInPtr = client->rcvBuf;
        client->lastIO = PR_Now();

        if (bytesRead > 0) {
                client->currentBytesAvailable = bytesRead;
                client->connectStatus = RECV_INITIAL;
                *pKeepGoing = PKIX_TRUE;
        } else {
                client->connectStatus = RECV_PENDING;
                *pKeepGoing = PKIX_FALSE;
        }

        PKIX_CHECK(PKIX_PL_Object_InvalidateCache
                ((PKIX_PL_Object *)client, plContext),
                PKIX_OBJECTINVALIDATECACHEFAILED);

cleanup:
        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_RecvContinue
 * DESCRIPTION:
 *
 *  This function determines whether the receiving of the LDAP-protocol message
 *  for the CertStore embodied in the LdapDefaultClient "client" has completed,
 *  and stores in "pKeepGoing" a flag indicating whether processing can continue
 *  without further input.
 *
 * PARAMETERS:
 *  "client"
 *      The address of the LdapDefaultClient object. Must be non-NULL.
 *  "pKeepGoing"
 *      The address at which the Boolean state machine flag is stored to
 *      indicate whether processing can continue without further input.
 *      Must be non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in a
 *      non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_RecvContinue(
        PKIX_PL_LdapDefaultClient *client,
        PKIX_Boolean *pKeepGoing,
        void *plContext)
{
        PKIX_Int32 bytesRead = 0;
        PKIX_PL_Socket_Callback *callbackList = NULL;

        PKIX_ENTER(LDAPDEFAULTCLIENT, "pkix_pl_LdapDefaultClient_RecvContinue");
        PKIX_NULLCHECK_TWO(client, pKeepGoing);

        callbackList = (PKIX_PL_Socket_Callback *)(client->callbackList);

        PKIX_CHECK(callbackList->pollCallback
                (client->clientSocket, NULL, &bytesRead, plContext),
                PKIX_SOCKETPOLLFAILED);

        if (bytesRead > 0) {
                client->currentBytesAvailable += bytesRead;
                client->connectStatus = RECV_INITIAL;
                *pKeepGoing = PKIX_TRUE;

                PKIX_CHECK(PKIX_PL_Object_InvalidateCache
                        ((PKIX_PL_Object *)client, plContext),
                        PKIX_OBJECTINVALIDATECACHEFAILED);
        } else {
                *pKeepGoing = PKIX_FALSE;
        }

cleanup:
        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_AbandonContinue
 * DESCRIPTION:
 *
 *  This function determines whether the abandon-message request of the
 *  LDAP-protocol message for the CertStore embodied in the LdapDefaultClient
 *  "client" has completed, and stores in "pKeepGoing" a flag indicating whether
 *  processing can continue without further input.
 *
 * PARAMETERS:
 *  "client"
 *      The address of the LdapDefaultClient object. Must be non-NULL.
 *  "pKeepGoing"
 *      The address at which the Boolean state machine flag is stored to
 *      indicate whether processing can continue without further input.
 *      Must be non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in a
 *      non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_AbandonContinue(
        PKIX_PL_LdapDefaultClient *client,
        PKIX_Boolean *pKeepGoing,
        void *plContext)
{
        PKIX_Int32 bytesWritten = 0;
        PKIX_PL_Socket_Callback *callbackList = NULL;

        PKIX_ENTER
                (LDAPDEFAULTCLIENT, "pkix_pl_LdapDefaultClient_AbandonContinue");
        PKIX_NULLCHECK_TWO(client, pKeepGoing);

        callbackList = (PKIX_PL_Socket_Callback *)(client->callbackList);

        PKIX_CHECK(callbackList->pollCallback
                (client->clientSocket, &bytesWritten, NULL, plContext),
                PKIX_SOCKETPOLLFAILED);

        if (bytesWritten > 0) {
                client->connectStatus = BOUND;
                *pKeepGoing = PKIX_TRUE;

                PKIX_CHECK(PKIX_PL_Object_InvalidateCache
                        ((PKIX_PL_Object *)client, plContext),
                        PKIX_OBJECTINVALIDATECACHEFAILED);
        } else {
                *pKeepGoing = PKIX_FALSE;
        }

cleanup:
        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_RecvInitial
 * DESCRIPTION:
 *
 *  This function processes the contents of the first buffer of a received
 *  LDAP-protocol message for the CertStore embodied in the LdapDefaultClient
 *  "client", and stores in "pKeepGoing" a flag indicating whether processing can
 *  continue without further input.
 *
 * PARAMETERS:
 *  "client"
 *      The address of the LdapDefaultClient object. Must be non-NULL.
 *  "pKeepGoing"
 *      The address at which the Boolean state machine flag is stored to
 *      indicate whether processing can continue without further input.
 *      Must be non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in a
 *      non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_RecvInitial(
        PKIX_PL_LdapDefaultClient *client,
        PKIX_Boolean *pKeepGoing,
        void *plContext)
{
        unsigned char *msgBuf = NULL;
        unsigned char *to = NULL;
        unsigned char *from = NULL;
        PKIX_UInt32 dataIndex = 0;
        PKIX_UInt32 messageIdLen = 0;
        PKIX_UInt32 messageLength = 0;
        PKIX_UInt32 sizeofLength = 0;
        PKIX_UInt32 bytesProcessed = 0;
        unsigned char messageChar = 0;
        LDAPMessageType messageType = 0;
        PKIX_Int32 bytesRead = 0;
        PKIX_PL_Socket_Callback *callbackList = NULL;

        PKIX_ENTER(LDAPDEFAULTCLIENT, "pkix_pl_LdapDefaultClient_RecvInitial");
        PKIX_NULLCHECK_TWO(client, pKeepGoing);

        /*
         * Is there an LDAPResponse in progress? I.e., have we
         * already processed the tag and length at the beginning of
         * the message?
         */
        if (client->currentResponse) {
                client->connectStatus = RECV_NONINITIAL;
                *pKeepGoing = PKIX_TRUE;
                goto cleanup;
        }
        msgBuf = client->currentInPtr;

        /* Do we have enough of the message to decode the message length? */
        if (client->currentBytesAvailable < MINIMUM_MSG_LENGTH) {
                /*
                 * No! Move these few bytes to the beginning of rcvBuf
                 * and hang another read.
                 */

                to = (unsigned char *)client->rcvBuf;
                from = client->currentInPtr;
                for (dataIndex = 0;
                    dataIndex < client->currentBytesAvailable;
                    dataIndex++) {
                        *to++ = *from++;
                }
                callbackList = (PKIX_PL_Socket_Callback *)(client->callbackList);
                PKIX_CHECK(callbackList->recvCallback
                        (client->clientSocket,
                        (void *)to,
                        client->capacity - client->currentBytesAvailable,
                        &bytesRead,
                        plContext),
                        PKIX_SOCKETRECVFAILED);

                client->currentInPtr = client->rcvBuf;
                client->lastIO = PR_Now();

                if (bytesRead <= 0) {
                        client->connectStatus = RECV_PENDING;
                        *pKeepGoing = PKIX_FALSE;
                        goto cleanup;
                } else {
                        client->currentBytesAvailable += bytesRead;
                }
        }

        /*
         * We have to determine whether the response is an entry, with
         * application-specific tag LDAP_SEARCHRESPONSEENTRY_TYPE, or a
         * resultCode, with application tag LDAP_SEARCHRESPONSERESULT_TYPE.
         * First, we have to figure out where to look for the tag.
         */

        /* Is the message length short form (one octet) or long form? */
        if ((msgBuf[1] & 0x80) != 0) {
                sizeofLength = msgBuf[1] & 0x7F;
                for (dataIndex = 0; dataIndex < sizeofLength; dataIndex++) {
                        messageLength =
                                (messageLength << 8) + msgBuf[dataIndex + 2];
                }
        } else {
                messageLength = msgBuf[1];
        }

        /* How many bytes did the messageID require? */
        messageIdLen = msgBuf[dataIndex + 3];

        messageChar = msgBuf[dataIndex + messageIdLen + 4];

        /* Are we looking at an Entry message or a ResultCode message? */
        if ((SEC_ASN1_CONSTRUCTED | SEC_ASN1_APPLICATION |
            LDAP_SEARCHRESPONSEENTRY_TYPE) == messageChar) {

                messageType = LDAP_SEARCHRESPONSEENTRY_TYPE;

        } else if ((SEC_ASN1_CONSTRUCTED | SEC_ASN1_APPLICATION |
            LDAP_SEARCHRESPONSERESULT_TYPE) == messageChar) {

                messageType = LDAP_SEARCHRESPONSERESULT_TYPE;

        } else {

                PKIX_ERROR(PKIX_SEARCHRESPONSEPACKETOFUNKNOWNTYPE);

        }

        /*
         * messageLength is the length from (tag, length, value).
         * We have to allocate space for the tag and length bits too.
         */
        PKIX_CHECK(pkix_pl_LdapResponse_Create
                (messageType,
                messageLength + dataIndex + 2,
                client->currentBytesAvailable,
                msgBuf,
                &bytesProcessed,
                &(client->currentResponse),
                plContext),
                PKIX_LDAPRESPONSECREATEFAILED);

        client->currentBytesAvailable -= bytesProcessed;

        PKIX_CHECK(pkix_pl_LdapDefaultClient_RecvCheckComplete
                (client, bytesProcessed, pKeepGoing, plContext),
                PKIX_LDAPDEFAULTCLIENTRECVCHECKCOMPLETEFAILED);

cleanup:

        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_RecvNonInitial
 * DESCRIPTION:
 *
 *  This function processes the contents of buffers, after the first, of a
 *  received LDAP-protocol message for the CertStore embodied in the
 *  LdapDefaultClient "client", and stores in "pKeepGoing" a flag indicating
 *  whether processing can continue without further input.
 *
 * PARAMETERS:
 *  "client"
 *      The address of the LdapDefaultClient object. Must be non-NULL.
 *  "pKeepGoing"
 *      The address at which the Boolean state machine flag is stored to
 *      indicate whether processing can continue without further input.
 *      Must be non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in a
 *      non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_RecvNonInitial(
        PKIX_PL_LdapDefaultClient *client,
        PKIX_Boolean *pKeepGoing,
        void *plContext)
{

        PKIX_UInt32 bytesProcessed = 0;

        PKIX_ENTER
                (LDAPDEFAULTCLIENT, "pkix_pl_LdapDefaultClient_RecvNonInitial");
        PKIX_NULLCHECK_TWO(client, pKeepGoing);

        PKIX_CHECK(pkix_pl_LdapResponse_Append
                (client->currentResponse,
                client->currentBytesAvailable,
                client->currentInPtr,
                &bytesProcessed,
                plContext),
                PKIX_LDAPRESPONSEAPPENDFAILED);

        client->currentBytesAvailable -= bytesProcessed;

        PKIX_CHECK(pkix_pl_LdapDefaultClient_RecvCheckComplete
                (client, bytesProcessed, pKeepGoing, plContext),
                PKIX_LDAPDEFAULTCLIENTRECVCHECKCOMPLETEFAILED);

cleanup:

        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_Dispatch
 * DESCRIPTION:
 *
 *  This function is the state machine dispatcher for the CertStore embodied in
 *  the LdapDefaultClient pointed to by "client". Results are returned by
 *  changes to various fields in the context.
 *
 * PARAMETERS:
 *  "client"
 *      The address of the LdapDefaultClient object. Must be non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in a
 *      non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_Dispatch(
        PKIX_PL_LdapDefaultClient *client,
        void *plContext)
{
        PKIX_UInt32 bytesTransferred = 0;
        PKIX_Boolean keepGoing = PKIX_TRUE;

        PKIX_ENTER(LDAPDEFAULTCLIENT, "pkix_pl_LdapDefaultClient_Dispatch");
        PKIX_NULLCHECK_ONE(client);

        while (keepGoing) {
                switch (client->connectStatus) {
                case CONNECT_PENDING:
                        PKIX_CHECK
                                (pkix_pl_LdapDefaultClient_ConnectContinue
                                (client, &keepGoing, plContext),
                                PKIX_LDAPDEFAULTCLIENTCONNECTCONTINUEFAILED);
                        break;
                case CONNECTED:
                        PKIX_CHECK
                                (pkix_pl_LdapDefaultClient_Bind
                                (client, &keepGoing, plContext),
                                PKIX_LDAPDEFAULTCLIENTBINDFAILED);
                        break;
                case BIND_PENDING:
                        PKIX_CHECK
                                (pkix_pl_LdapDefaultClient_BindContinue
                                (client, &keepGoing, plContext),
                                PKIX_LDAPDEFAULTCLIENTBINDCONTINUEFAILED);
                        break;
                case BIND_RESPONSE:
                        PKIX_CHECK
                                (pkix_pl_LdapDefaultClient_BindResponse
                                (client, &keepGoing, plContext),
                                PKIX_LDAPDEFAULTCLIENTBINDRESPONSEFAILED);
                        break;
                case BIND_RESPONSE_PENDING:
                        PKIX_CHECK
                                (pkix_pl_LdapDefaultClient_BindResponseContinue
                                (client, &keepGoing, plContext),
                                PKIX_LDAPDEFAULTCLIENTBINDRESPONSECONTINUEFAILED);
                        break;
                case BOUND:
                        PKIX_CHECK
                                (pkix_pl_LdapDefaultClient_Send
                                (client, &keepGoing, &bytesTransferred, plContext),
                                PKIX_LDAPDEFAULTCLIENTSENDFAILED);
                        break;
                case SEND_PENDING:
                        PKIX_CHECK
                                (pkix_pl_LdapDefaultClient_SendContinue
                                (client, &keepGoing, &bytesTransferred, plContext),
                                PKIX_LDAPDEFAULTCLIENTSENDCONTINUEFAILED);
                        break;
                case RECV:
                        PKIX_CHECK
                                (pkix_pl_LdapDefaultClient_Recv
                                (client, &keepGoing, plContext),
                                PKIX_LDAPDEFAULTCLIENTRECVFAILED);
                        break;
                case RECV_PENDING:
                        PKIX_CHECK
                                (pkix_pl_LdapDefaultClient_RecvContinue
                                (client, &keepGoing, plContext),
                                PKIX_LDAPDEFAULTCLIENTRECVCONTINUEFAILED);
                        break;
                case RECV_INITIAL:
                        PKIX_CHECK
                                (pkix_pl_LdapDefaultClient_RecvInitial
                                (client, &keepGoing, plContext),
                                PKIX_LDAPDEFAULTCLIENTRECVINITIALFAILED);
                        break;
                case RECV_NONINITIAL:
                        PKIX_CHECK
                                (pkix_pl_LdapDefaultClient_RecvNonInitial
                                (client, &keepGoing, plContext),
                                PKIX_LDAPDEFAULTCLIENTRECVNONINITIALFAILED);
                        break;
                case ABANDON_PENDING:
                        PKIX_CHECK
                                (pkix_pl_LdapDefaultClient_AbandonContinue
                                (client, &keepGoing, plContext),
                                PKIX_LDAPDEFAULTCLIENTABANDONCONTINUEFAILED);
                        break;
                default:
                        PKIX_ERROR(PKIX_LDAPCERTSTOREINILLEGALSTATE);
                }
        }

cleanup:

        PKIX_RETURN(LDAPDEFAULTCLIENT);
}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_MakeAndFilter
 * DESCRIPTION:
 *
 *  This function allocates space from the arena pointed to by "arena" to
 *  construct a filter that will match components of the X500Name pointed to by
 *  XXX...
 *
 * PARAMETERS:
 *  "arena"
 *      The address of the PLArenaPool used in creating the filter. Must be
 *       non-NULL.
 *  "nameComponent"
 *      The address of a NULL-terminated list of LDAPNameComponents
 *      Must be non-NULL.
 *  "pFilter"
 *      The address at which the result is stored.
 *  "plContext"
 *      Platform-specific context pointer
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a CertStore Error if the function fails in a non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_MakeAndFilter(
        PLArenaPool *arena,
        LDAPNameComponent **nameComponents,
        LDAPFilter **pFilter,
        void *plContext)
{
        LDAPFilter **setOfFilter;
        LDAPFilter *andFilter = NULL;
        LDAPFilter *currentFilter = NULL;
        PKIX_UInt32 componentsPresent = 0;
        void *v = NULL;
        unsigned char *component = NULL;
        LDAPNameComponent **componentP = NULL;

        PKIX_ENTER(CERTSTORE, "pkix_pl_LdapDefaultClient_MakeAndFilter");
        PKIX_NULLCHECK_THREE(arena, nameComponents, pFilter);

        /* count how many components we were provided */
        for (componentP = nameComponents, componentsPresent = 0;
                *(componentP++) != NULL;
                componentsPresent++) {}

        /* Space for (componentsPresent + 1) pointers to LDAPFilter */
        PKIX_PL_NSSCALLRV(CERTSTORE, v, PORT_ArenaZAlloc,
                (arena, (componentsPresent + 1)*sizeof(LDAPFilter *)));
        setOfFilter = (LDAPFilter **)v;

        /* Space for AndFilter and <componentsPresent> EqualFilters */
        PKIX_PL_NSSCALLRV(CERTSTORE, v, PORT_ArenaZNewArray,
                (arena, LDAPFilter, componentsPresent + 1));
        setOfFilter[0] = (LDAPFilter *)v;

        /* Claim the first array element for the ANDFilter */
        andFilter = setOfFilter[0];

        /* Set ANDFilter to point to the first EqualFilter pointer */
        andFilter->selector = LDAP_ANDFILTER_TYPE;
        andFilter->filter.andFilter.filters = setOfFilter;

        currentFilter = andFilter + 1;

        for (componentP = nameComponents, componentsPresent = 0;
                *(componentP) != NULL; componentP++) {
                setOfFilter[componentsPresent++] = currentFilter;
                currentFilter->selector = LDAP_EQUALFILTER_TYPE;
                component = (*componentP)->attrType;
                currentFilter->filter.equalFilter.attrType.data = component;
                currentFilter->filter.equalFilter.attrType.len = 
                        PL_strlen((const char *)component);
                component = (*componentP)->attrValue;
                currentFilter->filter.equalFilter.attrValue.data = component;
                currentFilter->filter.equalFilter.attrValue.len =
                        PL_strlen((const char *)component);
                currentFilter++;
        }

        setOfFilter[componentsPresent] = NULL;

        *pFilter = andFilter;

        PKIX_RETURN(CERTSTORE);

}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_InitiateRequest
 * DESCRIPTION:
 *
 *
 * PARAMETERS:
 *  "client"
 *      The address of the LdapDefaultClient object. Must be non-NULL.
 *  "requestParams"
 *      The address of an LdapClientParams object. Must be non-NULL.
 *  "pPollDesc"
 *      The location where the address of the PRPollDesc is stored, if the
 *      client returns with I/O pending.
 *  "pResponse"
 *      The address where the List of LDAPResponses, or NULL for an
 *      unfinished request, is stored. Must be non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in a
 *      non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_InitiateRequest(
        PKIX_PL_LdapClient *genericClient,
        LDAPRequestParams *requestParams,
        void **pPollDesc,
        PKIX_List **pResponse,
        void *plContext)
{
        PKIX_List *searchResponseList = NULL;
        SECItem *encoded = NULL;
        LDAPFilter *filter = NULL;
        PKIX_PL_LdapDefaultClient *client = 0;

        PKIX_ENTER
                (LDAPDEFAULTCLIENT,
                "pkix_pl_LdapDefaultClient_InitiateRequest");
        PKIX_NULLCHECK_FOUR(genericClient, requestParams, pPollDesc, pResponse);

        PKIX_CHECK(pkix_CheckType
                ((PKIX_PL_Object *)genericClient,
                PKIX_LDAPDEFAULTCLIENT_TYPE,
                plContext),
                PKIX_GENERICCLIENTNOTANLDAPDEFAULTCLIENT);

        client = (PKIX_PL_LdapDefaultClient *)genericClient;

        PKIX_CHECK(pkix_pl_LdapDefaultClient_MakeAndFilter
                (client->arena, requestParams->nc, &filter, plContext),
                PKIX_LDAPDEFAULTCLIENTMAKEANDFILTERFAILED);

        PKIX_CHECK(pkix_pl_LdapRequest_Create
                (client->arena,
                client->messageID++,
                requestParams->baseObject,
                requestParams->scope,
                requestParams->derefAliases,
                requestParams->sizeLimit,
                requestParams->timeLimit,
                PKIX_FALSE,    /* attrs only */
                filter,
                requestParams->attributes,
                &client->currentRequest,
                plContext),
                PKIX_LDAPREQUESTCREATEFAILED);

        /* check hashtable for matching request */
        PKIX_CHECK(PKIX_PL_HashTable_Lookup
                (client->cachePtr,
                (PKIX_PL_Object *)(client->currentRequest),
                (PKIX_PL_Object **)&searchResponseList,
                plContext),
                PKIX_HASHTABLELOOKUPFAILED);

        if (searchResponseList != NULL) {
                *pPollDesc = NULL;
                *pResponse = searchResponseList;
                PKIX_DECREF(client->currentRequest);
                goto cleanup;
        }

        /* It wasn't cached. We'll have to actually send it. */

        PKIX_CHECK(pkix_pl_LdapRequest_GetEncoded
                (client->currentRequest, &encoded, plContext),
                PKIX_LDAPREQUESTGETENCODEDFAILED);

        client->sendBuf = encoded->data;
        client->bytesToWrite = encoded->len;

        PKIX_CHECK(pkix_pl_LdapDefaultClient_Dispatch(client, plContext),
                PKIX_LDAPDEFAULTCLIENTDISPATCHFAILED);

        /*
         * It's not enough that we may be done with a particular read.
         * We're still processing the transaction until we've gotten the
         * SearchResponseResult message and returned to the BOUND state.
         * Otherwise we must still have a read pending, and must hold off
         * on returning results.
         */
        if ((client->connectStatus == BOUND) &&
	    (client->entriesFound != NULL)) {
                *pPollDesc = NULL;
                *pResponse = client->entriesFound;
                client->entriesFound = NULL;
                PKIX_DECREF(client->currentRequest);
        } else {
                *pPollDesc = &client->pollDesc;
                *pResponse = NULL;
        }

cleanup:

        PKIX_RETURN(LDAPDEFAULTCLIENT);

}

/*
 * FUNCTION: pkix_pl_LdapDefaultClient_ResumeRequest
 * DESCRIPTION:
 *
 *
 * PARAMETERS:
 *  "client"
 *      The address of the LdapDefaultClient object. Must be non-NULL.
 *  "pPollDesc"
 *      The location where the address of the PRPollDesc is stored, if the
 *      client returns with I/O pending.
 *  "pResponse"
 *      The address where the List of LDAPResponses, or NULL for an
 *      unfinished request, is stored. Must be non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a LdapDefaultClient Error if the function fails in a
 *      non-fatal way.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
static PKIX_Error *
pkix_pl_LdapDefaultClient_ResumeRequest(
        PKIX_PL_LdapClient *genericClient,
        void **pPollDesc,
        PKIX_List **pResponse,
        void *plContext)
{
        PKIX_PL_LdapDefaultClient *client = 0;

        PKIX_ENTER
                (LDAPDEFAULTCLIENT, "pkix_pl_LdapDefaultClient_ResumeRequest");
        PKIX_NULLCHECK_THREE(genericClient, pPollDesc, pResponse);

        PKIX_CHECK(pkix_CheckType
                ((PKIX_PL_Object *)genericClient,
                PKIX_LDAPDEFAULTCLIENT_TYPE,
                plContext),
                PKIX_GENERICCLIENTNOTANLDAPDEFAULTCLIENT);

        client = (PKIX_PL_LdapDefaultClient *)genericClient;

        PKIX_CHECK(pkix_pl_LdapDefaultClient_Dispatch(client, plContext),
                PKIX_LDAPDEFAULTCLIENTDISPATCHFAILED);

        /*
         * It's not enough that we may be done with a particular read.
         * We're still processing the transaction until we've gotten the
         * SearchResponseResult message and returned to the BOUND state.
         * Otherwise we must still have a read pending, and must hold off
         * on returning results.
         */
        if ((client->connectStatus == BOUND) &&
	    (client->entriesFound != NULL)) {
                *pPollDesc = NULL;
                *pResponse = client->entriesFound;
                client->entriesFound = NULL;
                PKIX_DECREF(client->currentRequest);
        } else {
                *pPollDesc = &client->pollDesc;
                *pResponse = NULL;
        }

cleanup:

        PKIX_RETURN(LDAPDEFAULTCLIENT);

}

/* --Public-LdapDefaultClient-Functions----------------------------------- */

/*
 * FUNCTION: PKIX_PL_LdapDefaultClient_AbandonRequest
 * DESCRIPTION:
 *
 *  This function creates and sends an LDAP-protocol "Abandon" message to the 
 *  server connected to the LdapDefaultClient pointed to by "client".
 *
 * PARAMETERS:
 *  "client"
 *      The LdapDefaultClient whose connection is to be abandoned. Must be
 *      non-NULL.
 *  "plContext"
 *      Platform-specific context pointer.
 * THREAD SAFETY:
 *  Thread Safe (see Thread Safety Definitions in Programmer's Guide)
 * RETURNS:
 *  Returns NULL if the function succeeds.
 *  Returns a Fatal Error if the function fails in an unrecoverable way.
 */
PKIX_Error *
PKIX_PL_LdapDefaultClient_AbandonRequest(
        PKIX_PL_LdapDefaultClient *client,
        void *plContext)
{
        PKIX_Int32 bytesWritten = 0;
        PKIX_PL_Socket_Callback *callbackList = NULL;
        SECItem *encoded = NULL;

        PKIX_ENTER(CERTSTORE, "PKIX_PL_LdapDefaultClient_AbandonRequest");
        PKIX_NULLCHECK_ONE(client);

        if (client->connectStatus == RECV_PENDING) {
                PKIX_CHECK(pkix_pl_LdapDefaultClient_MakeAbandon
                        (client->arena,
                        (client->messageID) - 1,
                        &encoded,
                        plContext),
                        PKIX_LDAPDEFAULTCLIENTMAKEABANDONFAILED);

                callbackList = (PKIX_PL_Socket_Callback *)(client->callbackList);
                PKIX_CHECK(callbackList->sendCallback
                        (client->clientSocket,
                        encoded->data,
                        encoded->len,
                        &bytesWritten,
                        plContext),
                        PKIX_SOCKETSENDFAILED);

                if (bytesWritten < 0) {
                        client->connectStatus = ABANDON_PENDING;
                } else {
                        client->connectStatus = BOUND;
                }
        }

        PKIX_DECREF(client->entriesFound);
        PKIX_DECREF(client->currentRequest);
        PKIX_DECREF(client->currentResponse);

cleanup:

        PKIX_DECREF(client);

        PKIX_RETURN(CERTSTORE);
}
