9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync/** @file
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync *
45c94fd5bc3ee64a3577f858c7eca5a566601c6fvboxsync * VirtualBox External Authentication Library:
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync * Mac OS X Authentication. This is based on
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync * http://developer.apple.com/mac/library/samplecode/CryptNoMore/
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync/*
45c94fd5bc3ee64a3577f858c7eca5a566601c6fvboxsync * Copyright (C) 2009-2011 Oracle Corporation
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync *
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync * This file is part of VirtualBox Open Source Edition (OSE), as
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync * available from http://www.virtualbox.org. This file is free software;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync * you can redistribute it and/or modify it under the terms of the GNU
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync * General Public License (GPL) as published by the Free Software
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync * Foundation, in version 2 as it comes in the "COPYING" file of the
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync#include <iprt/cdefs.h>
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync#include <iprt/assert.h>
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync
b8908d384db2324f04a2f68a13e67ea32ebf609avboxsync#include <VBox/VBoxAuth.h>
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync#include <DirectoryService/DirectoryService.h>
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync/* Globals */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsyncstatic const size_t s_cBufferSize = 32 * 1024;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsynctDirStatus defaultSearchNodePath(tDirReference pDirRef, tDataListPtr *pdsNodePath)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync{
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tDirStatus dsErr = eDSNoErr;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Create a buffer for the resulting nodes */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tDataBufferPtr pTmpBuf = NULL;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync pTmpBuf = dsDataBufferAllocate(pDirRef, s_cBufferSize);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (pTmpBuf)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Try to find the default search node for local names */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync UInt32 cNodes;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tContextData pCtx = NULL;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsErr = dsFindDirNodes(pDirRef, pTmpBuf, NULL, eDSLocalNodeNames, &cNodes, &pCtx);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Any nodes found? */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if ( dsErr == eDSNoErr
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync && cNodes >= 1)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* The first path of the node list is what we looking for. */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsErr = dsGetDirNodeName(pDirRef, pTmpBuf, 1, pdsNodePath);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync else
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsErr = eDSNodeNotFound;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (pCtx)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsReleaseContinueData(pDirRef, pCtx);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsDataBufferDeAllocate(pDirRef, pTmpBuf);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync else
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsErr = eDSAllocationFailed;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync return dsErr;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync}
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsynctDirStatus userAuthInfo(tDirReference pDirRef, tDirNodeReference pNodeRef, const char *pszUsername, tDataListPtr *ppAuthNodeListOut)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync{
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tDirStatus dsErr = eDSNoErr;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tDirStatus dsCleanErr = eDSNoErr;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Create a buffer for the resulting authentication info */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tDataBufferPtr pTmpBuf = dsDataBufferAllocate(pDirRef, s_cBufferSize);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (pTmpBuf)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Create the necessary lists for kDSNAttrMetaNodeLocation and kDSNAttrRecordName. */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tDataListPtr pRecordType = dsBuildListFromStrings(pDirRef, kDSStdRecordTypeUsers, NULL);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tDataListPtr pRecordName = dsBuildListFromStrings(pDirRef, pszUsername, NULL);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tDataListPtr pRequestedAttributes = dsBuildListFromStrings(pDirRef, kDSNAttrMetaNodeLocation, kDSNAttrRecordName, NULL);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (!( pRecordType == NULL
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync || pRecordName == NULL
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync || pRequestedAttributes == NULL))
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Now search for the first matching record */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync UInt32 cRecords = 1;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tContextData pCtx = NULL;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsErr = dsGetRecordList(pNodeRef,
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync pTmpBuf,
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync pRecordName,
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync eDSExact,
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync pRecordType,
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync pRequestedAttributes,
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync false,
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync &cRecords,
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync &pCtx);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if ( dsErr == eDSNoErr
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync && cRecords >= 1)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Process the first found record. Look at any attribute one by one. */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tAttributeListRef pRecAttrListRef = NULL;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tRecordEntryPtr pRecEntry = NULL;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tDataListPtr pAuthNodeList = NULL;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsErr = dsGetRecordEntry(pNodeRef, pTmpBuf, 1, &pRecAttrListRef, &pRecEntry);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (dsErr == eDSNoErr)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync for (size_t i = 1; i <= pRecEntry->fRecordAttributeCount; ++i)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tAttributeValueListRef pAttrValueListRef = NULL;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tAttributeEntryPtr pAttrEntry = NULL;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Get the information for this attribute. */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsErr = dsGetAttributeEntry(pNodeRef, pTmpBuf, pRecAttrListRef, i,
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync &pAttrValueListRef, &pAttrEntry);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (dsErr == eDSNoErr)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tAttributeValueEntryPtr pValueEntry = NULL;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Has any value? */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (pAttrEntry->fAttributeValueCount > 0)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsErr = dsGetAttributeValue(pNodeRef, pTmpBuf, 1, pAttrValueListRef, &pValueEntry);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (dsErr == eDSNoErr)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Check for kDSNAttrMetaNodeLocation */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (strcmp(pAttrEntry->fAttributeSignature.fBufferData, kDSNAttrMetaNodeLocation) == 0)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Convert the meta location attribute to a path node list */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync pAuthNodeList = dsBuildFromPath(pDirRef,
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync pValueEntry->fAttributeValueData.fBufferData,
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync "/");
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (pAuthNodeList == NULL)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsErr = eDSAllocationFailed;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (pValueEntry != NULL)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsDeallocAttributeValueEntry(pDirRef, pValueEntry);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (pAttrValueListRef)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsCloseAttributeValueList(pAttrValueListRef);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (pAttrEntry != NULL)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsDeallocAttributeEntry(pDirRef, pAttrEntry);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (dsErr != eDSNoErr)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync break;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Copy the results */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (dsErr == eDSNoErr)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (pAuthNodeList != NULL)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Copy out results. */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync *ppAuthNodeListOut = pAuthNodeList;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync pAuthNodeList = NULL;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync else
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsErr = eDSAttributeNotFound;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (pAuthNodeList != NULL)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsCleanErr = dsDataListDeallocate(pDirRef, pAuthNodeList);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (dsCleanErr == eDSNoErr)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync free(pAuthNodeList);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (pRecAttrListRef)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsCloseAttributeList(pRecAttrListRef);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (pRecEntry != NULL)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsDeallocRecordEntry(pDirRef, pRecEntry);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync else
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsErr = eDSRecordNotFound;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (pCtx)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsReleaseContinueData(pDirRef, pCtx);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync else
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsErr = eDSAllocationFailed;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (pRequestedAttributes != NULL)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsCleanErr = dsDataListDeallocate(pDirRef, pRequestedAttributes);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (dsCleanErr == eDSNoErr)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync free(pRequestedAttributes);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (pRecordName != NULL)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsCleanErr = dsDataListDeallocate(pDirRef, pRecordName);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (dsCleanErr == eDSNoErr)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync free(pRecordName);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (pRecordType != NULL)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsCleanErr = dsDataListDeallocate(pDirRef, pRecordType);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (dsCleanErr == eDSNoErr)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync free(pRecordType);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsDataBufferDeAllocate(pDirRef, pTmpBuf);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync else
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsErr = eDSAllocationFailed;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync return dsErr;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync}
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsynctDirStatus authWithNode(tDirReference pDirRef, tDataListPtr pAuthNodeList, const char *pszUsername, const char *pszPassword)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync{
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tDirStatus dsErr = eDSNoErr;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Open the authentication node. */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tDirNodeReference pAuthNodeRef = NULL;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsErr = dsOpenDirNode(pDirRef, pAuthNodeList, &pAuthNodeRef);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (dsErr == eDSNoErr)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* How like we to authenticate! */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tDataNodePtr pAuthMethod = dsDataNodeAllocateString(pDirRef, kDSStdAuthNodeNativeClearTextOK);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (pAuthMethod)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Create the memory holding the authentication data. The data
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync * structure consists of 4 byte length of the username + zero byte,
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync * the username itself, a 4 byte length of the password & the
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync * password itself + zero byte. */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tDataBufferPtr pAuthOutBuf = dsDataBufferAllocate(pDirRef, s_cBufferSize);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (pAuthOutBuf)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync size_t cUserName = strlen(pszUsername) + 1;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync size_t cPassword = strlen(pszPassword) + 1;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync unsigned long cLen = 0;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tDataBufferPtr pAuthInBuf = dsDataBufferAllocate(pDirRef, sizeof(cLen) + cUserName + sizeof(cLen) + cPassword);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (pAuthInBuf)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Move the data into the buffer. */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync pAuthInBuf->fBufferLength = 0;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Length of the username */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync cLen = cUserName;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync memcpy(&pAuthInBuf->fBufferData[pAuthInBuf->fBufferLength], &cLen, sizeof(cLen));
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync pAuthInBuf->fBufferLength += sizeof(cLen);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* The username itself */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync memcpy(&pAuthInBuf->fBufferData[pAuthInBuf->fBufferLength], pszUsername, cUserName);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync pAuthInBuf->fBufferLength += cUserName;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Length of the password */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync cLen = cPassword;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync memcpy(&pAuthInBuf->fBufferData[pAuthInBuf->fBufferLength], &cLen, sizeof(cLen));
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync pAuthInBuf->fBufferLength += sizeof(cLen);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* The password itself */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync memcpy(&pAuthInBuf->fBufferData[pAuthInBuf->fBufferLength], pszPassword, cPassword);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync pAuthInBuf->fBufferLength += cPassword;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Now authenticate */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsErr = dsDoDirNodeAuth(pAuthNodeRef, pAuthMethod, true, pAuthInBuf, pAuthOutBuf, NULL);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Clean up. */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsDataBufferDeAllocate(pDirRef, pAuthInBuf);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync else
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsErr = eDSAllocationFailed;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsDataBufferDeAllocate(pDirRef, pAuthOutBuf);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync else
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsErr = eDSAllocationFailed;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsDataNodeDeAllocate(pDirRef, pAuthMethod);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync else
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsErr = eDSAllocationFailed;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsCloseDirNode(pAuthNodeRef);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync return dsErr;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync}
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsyncRT_C_DECLS_BEGIN
45c94fd5bc3ee64a3577f858c7eca5a566601c6fvboxsyncDECLEXPORT(AuthResult) AUTHCALL AuthEntry(const char *szCaller,
45c94fd5bc3ee64a3577f858c7eca5a566601c6fvboxsync PAUTHUUID pUuid,
45c94fd5bc3ee64a3577f858c7eca5a566601c6fvboxsync AuthGuestJudgement guestJudgement,
45c94fd5bc3ee64a3577f858c7eca5a566601c6fvboxsync const char *szUser,
45c94fd5bc3ee64a3577f858c7eca5a566601c6fvboxsync const char *szPassword,
45c94fd5bc3ee64a3577f858c7eca5a566601c6fvboxsync const char *szDomain,
45c94fd5bc3ee64a3577f858c7eca5a566601c6fvboxsync int fLogon,
45c94fd5bc3ee64a3577f858c7eca5a566601c6fvboxsync unsigned clientId)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync{
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Validate input */
289566e681dae45f110170f26eaa0bff964e50f9vboxsync AssertPtrReturn(szUser, AuthResultAccessDenied);
289566e681dae45f110170f26eaa0bff964e50f9vboxsync AssertPtrReturn(szPassword, AuthResultAccessDenied);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Result to a default value */
8b98c71a5a01d215eafbc3605cb7a66cc91ea774vboxsync AuthResult result = AuthResultAccessDenied;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync
45c94fd5bc3ee64a3577f858c7eca5a566601c6fvboxsync /* Only process logon requests. */
45c94fd5bc3ee64a3577f858c7eca5a566601c6fvboxsync if (!fLogon)
45c94fd5bc3ee64a3577f858c7eca5a566601c6fvboxsync return result; /* Return value is ignored by the caller. */
45c94fd5bc3ee64a3577f858c7eca5a566601c6fvboxsync
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tDirStatus dsErr = eDSNoErr;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tDirStatus dsCleanErr = eDSNoErr;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tDirReference pDirRef = NULL;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Connect to the Directory Service. */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsErr = dsOpenDirService(&pDirRef);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (dsErr == eDSNoErr)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Fetch the default search node */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tDataListPtr pSearchNodeList = NULL;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsErr = defaultSearchNodePath(pDirRef, &pSearchNodeList);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (dsErr == eDSNoErr)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Open the default search node */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tDirNodeReference pSearchNodeRef = NULL;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsErr = dsOpenDirNode(pDirRef, pSearchNodeList, &pSearchNodeRef);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (dsErr == eDSNoErr)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Search for the user info, fetch the authentication node &
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync * the authentication user name. This allows the client to
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync * specify a long user name even if the name which is used to
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync * authenticate has the short form. */
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync tDataListPtr pAuthNodeList = NULL;
289566e681dae45f110170f26eaa0bff964e50f9vboxsync dsErr = userAuthInfo(pDirRef, pSearchNodeRef, szUser, &pAuthNodeList);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (dsErr == eDSNoErr)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync {
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync /* Open the authentication node and do the authentication. */
289566e681dae45f110170f26eaa0bff964e50f9vboxsync dsErr = authWithNode(pDirRef, pAuthNodeList, szUser, szPassword);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (dsErr == eDSNoErr)
8b98c71a5a01d215eafbc3605cb7a66cc91ea774vboxsync result = AuthResultAccessGranted;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsCleanErr = dsDataListDeallocate(pDirRef, pAuthNodeList);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (dsCleanErr == eDSNoErr)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync free(pAuthNodeList);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsCloseDirNode(pSearchNodeRef);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsCleanErr = dsDataListDeallocate(pDirRef, pSearchNodeList);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync if (dsCleanErr == eDSNoErr)
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync free(pSearchNodeList);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync dsCloseDirService(pDirRef);
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync }
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync return result;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync}
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsyncRT_C_DECLS_END
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync
45c94fd5bc3ee64a3577f858c7eca5a566601c6fvboxsyncstatic PAUTHENTRY3 gpfnAuthEntry = AuthEntry;
9c0076729ec8138e89ce8a6af9a772b68f1f8dc7vboxsync