You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
1078 lines
28 KiB
1078 lines
28 KiB
//+-------------------------------------------------------------------------
|
|
//
|
|
// Microsoft Windows
|
|
//
|
|
// Copyright (C) Microsoft Corporation, 1996 - 1999
|
|
//
|
|
// File: mscatapi.cpp
|
|
//
|
|
// Contents: Microsoft Internet Security Catalog Utilities
|
|
//
|
|
// Functions: CryptCATOpen
|
|
// CryptCATClose
|
|
// CryptCATStoreFromHandle
|
|
// CryptCATGetMemberInfo
|
|
// CryptCATPutMemberInfo
|
|
// CryptCATVerifyMember
|
|
// CryptCATGetAttrInfo
|
|
// CryptCATPutAttrInfo
|
|
// CryptCATEnumerateMember
|
|
// CryptCATEnumerateAttr
|
|
//
|
|
// *** local functions ***
|
|
//
|
|
// CryptCATCreateStore
|
|
// CryptCATOpenStore
|
|
// FillNameValue
|
|
// CatalogCheckForDuplicateMember
|
|
//
|
|
// History: 29-Apr-1997 pberkman created
|
|
//
|
|
//--------------------------------------------------------------------------
|
|
|
|
#include "global.hxx"
|
|
#include "mscat32.h"
|
|
|
|
|
|
BOOL CryptCATCreateStore(CRYPTCATSTORE *pCat, LPWSTR pwszCatFile);
|
|
BOOL CryptCATOpenStore(CRYPTCATSTORE *pCat, LPWSTR pwszCatFile);
|
|
BOOL FillNameValue(CRYPTCATSTORE *pCatStore, CRYPTCATATTRIBUTE *pAttr);
|
|
BOOL CatalogCheckForDuplicateMember(Stack_ *pMembers, WCHAR *pwszReferenceTag);
|
|
|
|
|
|
/////////////////////////////////////////////////////////////////////////////
|
|
//
|
|
// Exported Functions
|
|
//
|
|
|
|
HANDLE WINAPI CryptCATOpen(LPWSTR pwszCatFile, DWORD fdwOpenFlags, HCRYPTPROV hProv,
|
|
DWORD dwPublicVersion, DWORD dwEncodingType)
|
|
{
|
|
CRYPTCATSTORE *pCatStore;
|
|
|
|
if (!(pwszCatFile))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return((HANDLE)INVALID_HANDLE_VALUE);
|
|
}
|
|
|
|
if (!(pCatStore = (CRYPTCATSTORE *)CatalogNew(sizeof(CRYPTCATSTORE))))
|
|
{
|
|
return((HANDLE)INVALID_HANDLE_VALUE);
|
|
}
|
|
|
|
memset(pCatStore, 0x00, sizeof(CRYPTCATSTORE));
|
|
|
|
pCatStore->cbStruct = sizeof(CRYPTCATSTORE);
|
|
pCatStore->hProv = hProv;
|
|
pCatStore->dwPublicVersion = (dwPublicVersion) ? dwPublicVersion : 0x00000100;
|
|
pCatStore->dwEncodingType = (dwEncodingType) ? dwEncodingType :
|
|
PKCS_7_ASN_ENCODING | X509_ASN_ENCODING;
|
|
|
|
if (!(hProv))
|
|
{
|
|
pCatStore->hProv = I_CryptGetDefaultCryptProv(0); // get the default and DONT RELEASE IT!!!!
|
|
|
|
if (!(pCatStore->hProv))
|
|
{
|
|
goto ErrorReturn;
|
|
}
|
|
}
|
|
|
|
if (fdwOpenFlags & CRYPTCAT_OPEN_CREATENEW)
|
|
{
|
|
if (!CryptCATCreateStore(pCatStore, pwszCatFile))
|
|
{
|
|
goto ErrorReturn;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
BOOL fRet;
|
|
|
|
fRet = CryptCATOpenStore(pCatStore, pwszCatFile);
|
|
|
|
if (!(fRet) && (fdwOpenFlags & CRYPTCAT_OPEN_ALWAYS))
|
|
{
|
|
fRet = CryptCATCreateStore(pCatStore, pwszCatFile);
|
|
}
|
|
|
|
if (fRet == FALSE)
|
|
{
|
|
goto ErrorReturn;
|
|
}
|
|
}
|
|
|
|
return((HANDLE)pCatStore);
|
|
|
|
ErrorReturn:
|
|
|
|
DWORD dwLastError;
|
|
|
|
dwLastError = GetLastError();
|
|
CryptCATClose((HANDLE)pCatStore);
|
|
SetLastError(dwLastError);
|
|
|
|
return(INVALID_HANDLE_VALUE);
|
|
}
|
|
|
|
BOOL WINAPI CryptCATClose(HANDLE hCatalog)
|
|
{
|
|
if (!(hCatalog) ||
|
|
(hCatalog == INVALID_HANDLE_VALUE))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(FALSE);
|
|
}
|
|
|
|
CRYPTCATSTORE *pCatStore;
|
|
|
|
pCatStore = (CRYPTCATSTORE *)hCatalog;
|
|
|
|
__try
|
|
{
|
|
if (!(_ISINSTRUCT(CRYPTCATSTORE, pCatStore->cbStruct, hReserved)))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(FALSE);
|
|
}
|
|
}
|
|
__except(EXCEPTION_EXECUTE_HANDLER)
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(FALSE);
|
|
}
|
|
|
|
BOOL fRet;
|
|
DWORD dwlerr;
|
|
|
|
dwlerr = GetLastError();
|
|
|
|
fRet = TRUE;
|
|
|
|
//
|
|
// file name
|
|
//
|
|
DELETE_OBJECT(pCatStore->pwszP7File);
|
|
|
|
//
|
|
// attributes
|
|
//
|
|
if (_ISINSTRUCT(CRYPTCATSTORE, pCatStore->cbStruct, hAttrs))
|
|
{
|
|
if (pCatStore->hAttrs)
|
|
{
|
|
Stack_ *ps;
|
|
DWORD cStack;
|
|
CRYPTCATATTRIBUTE *pAttr;
|
|
|
|
ps = (Stack_ *)pCatStore->hAttrs;
|
|
|
|
cStack = 0;
|
|
|
|
while (pAttr = (CRYPTCATATTRIBUTE *)ps->Get(cStack))
|
|
{
|
|
CatalogFreeAttribute(pAttr);
|
|
|
|
cStack++;
|
|
}
|
|
|
|
DELETE_OBJECT(ps);
|
|
|
|
pCatStore->hAttrs = NULL;
|
|
}
|
|
}
|
|
|
|
//
|
|
// check hReserved to see if we used pStack
|
|
//
|
|
if (pCatStore->hReserved)
|
|
{
|
|
Stack_ *pStack;
|
|
CRYPTCATMEMBER *pCatMember;
|
|
DWORD dwCurPos;
|
|
|
|
pStack = (Stack_ *)pCatStore->hReserved;
|
|
|
|
dwCurPos = 0;
|
|
|
|
while (pCatMember = (CRYPTCATMEMBER *)pStack->Get(dwCurPos))
|
|
{
|
|
CatalogFreeMember(pCatMember);
|
|
|
|
dwCurPos++;
|
|
}
|
|
|
|
DELETE_OBJECT(pStack);
|
|
|
|
pCatStore->hReserved = NULL;
|
|
}
|
|
|
|
pCatStore->cbStruct = 0; // just in case they try to re-open it!
|
|
|
|
DELETE_OBJECT(pCatStore);
|
|
|
|
//
|
|
// restore last error
|
|
//
|
|
SetLastError(dwlerr);
|
|
|
|
return(fRet);
|
|
}
|
|
|
|
CRYPTCATSTORE * WINAPI CryptCATStoreFromHandle(IN HANDLE hCatalog)
|
|
{
|
|
return((CRYPTCATSTORE *)hCatalog);
|
|
}
|
|
|
|
HANDLE WINAPI CryptCATHandleFromStore(IN CRYPTCATSTORE *pCatStore)
|
|
{
|
|
return((HANDLE)pCatStore);
|
|
}
|
|
|
|
BOOL WINAPI CryptCATPersistStore(IN HANDLE hCatalog)
|
|
{
|
|
CRYPTCATSTORE *pStore;
|
|
|
|
if (!(hCatalog) ||
|
|
(hCatalog == INVALID_HANDLE_VALUE))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(FALSE);
|
|
}
|
|
|
|
pStore = CryptCATStoreFromHandle(hCatalog);
|
|
|
|
if (!(pStore->pwszP7File))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(FALSE);
|
|
}
|
|
|
|
return(CatalogSaveP7UData(pStore));
|
|
}
|
|
|
|
CRYPTCATATTRIBUTE * WINAPI CryptCATGetCatAttrInfo(HANDLE hCatalog, LPWSTR pwszReferenceTag)
|
|
{
|
|
CRYPTCATATTRIBUTE *pAttr;
|
|
CRYPTCATSTORE *pCatStore;
|
|
|
|
pAttr = NULL;
|
|
|
|
if (!(hCatalog) ||
|
|
(hCatalog == INVALID_HANDLE_VALUE) ||
|
|
!(pwszReferenceTag))
|
|
{
|
|
goto ErrorInvalidParam;
|
|
}
|
|
|
|
pCatStore = CryptCATStoreFromHandle(hCatalog);
|
|
|
|
|
|
if (!(_ISINSTRUCT(CRYPTCATSTORE, pCatStore->cbStruct, hAttrs)))
|
|
{
|
|
goto ErrorInvalidParam;
|
|
}
|
|
|
|
while (pAttr = CryptCATEnumerateCatAttr(hCatalog, pAttr))
|
|
{
|
|
if (pAttr->pwszReferenceTag)
|
|
{
|
|
if (_wcsicmp(pwszReferenceTag, pAttr->pwszReferenceTag) == 0)
|
|
{
|
|
goto CommonReturn;
|
|
}
|
|
}
|
|
}
|
|
|
|
goto ErrorNotFound;
|
|
|
|
CommonReturn:
|
|
ErrorReturn:
|
|
return(pAttr);
|
|
|
|
SET_ERROR_VAR_EX(DBG_SS, ErrorInvalidParam, ERROR_INVALID_PARAMETER);
|
|
SET_ERROR_VAR_EX(DBG_SS, ErrorNotFound, CRYPT_E_NOT_FOUND);
|
|
}
|
|
|
|
CRYPTCATATTRIBUTE * WINAPI CryptCATPutCatAttrInfo(HANDLE hCatalog, LPWSTR pwszReferenceTag,
|
|
DWORD dwAttrTypeAndAction, DWORD cbData,
|
|
BYTE *pbData)
|
|
{
|
|
CRYPTCATATTRIBUTE *pAttr;
|
|
|
|
pAttr = NULL;
|
|
|
|
if (!(hCatalog) ||
|
|
(hCatalog == INVALID_HANDLE_VALUE) ||
|
|
!(pwszReferenceTag) ||
|
|
((cbData > 0) && !(pbData)))
|
|
{
|
|
goto ErrorInvalidParam;
|
|
}
|
|
|
|
if (!(dwAttrTypeAndAction & CRYPTCAT_ATTR_DATABASE64) &&
|
|
!(dwAttrTypeAndAction & CRYPTCAT_ATTR_DATAASCII) &&
|
|
!(dwAttrTypeAndAction & CRYPTCAT_ATTR_DATAREPLACE))
|
|
{
|
|
goto ErrorInvalidParam;
|
|
}
|
|
|
|
CRYPTCATSTORE *pCatStore;
|
|
|
|
pCatStore = (CRYPTCATSTORE *)hCatalog;
|
|
|
|
if (!(_ISINSTRUCT(CRYPTCATSTORE, pCatStore->cbStruct, hAttrs)))
|
|
{
|
|
goto ErrorInvalidParam;
|
|
}
|
|
|
|
Stack_ *pStack;
|
|
|
|
if (!(pCatStore->hAttrs))
|
|
{
|
|
pStack = new Stack_(&MSCAT_CriticalSection);
|
|
|
|
if (!(pStack))
|
|
{
|
|
goto ErrorMemory;
|
|
}
|
|
|
|
pCatStore->hAttrs = (HANDLE)pStack;
|
|
}
|
|
|
|
pStack = (Stack_ *)pCatStore->hAttrs;
|
|
|
|
if (!(dwAttrTypeAndAction & CRYPTCAT_ATTR_DATAREPLACE))
|
|
{
|
|
if (!(pAttr = (CRYPTCATATTRIBUTE *)pStack->Add(sizeof(CRYPTCATATTRIBUTE))))
|
|
{
|
|
goto StackError;
|
|
}
|
|
|
|
memset(pAttr, 0x00, sizeof(CRYPTCATATTRIBUTE));
|
|
|
|
pAttr->cbStruct = sizeof(CRYPTCATATTRIBUTE);
|
|
|
|
if (!(pAttr->pwszReferenceTag = (LPWSTR)CatalogNew((wcslen(pwszReferenceTag) + 1) *
|
|
sizeof(WCHAR))))
|
|
{
|
|
goto ErrorMemory;
|
|
}
|
|
|
|
wcscpy(pAttr->pwszReferenceTag, pwszReferenceTag);
|
|
|
|
pAttr->dwAttrTypeAndAction = dwAttrTypeAndAction;
|
|
|
|
if (pbData)
|
|
{
|
|
if (dwAttrTypeAndAction & CRYPTCAT_ATTR_DATABASE64)
|
|
{
|
|
CryptStringToBinaryW((WCHAR *)pbData, cbData / sizeof(WCHAR), CRYPT_STRING_ANY, NULL, &pAttr->cbValue, NULL, NULL);
|
|
|
|
if (pAttr->cbValue < 1)
|
|
{
|
|
goto DecodeError;
|
|
}
|
|
|
|
if (!(pAttr->pbValue = (BYTE *)CatalogNew(pAttr->cbValue)))
|
|
{
|
|
pAttr->cbValue = 0;
|
|
goto ErrorMemory;
|
|
}
|
|
|
|
if (!CryptStringToBinaryW((WCHAR *)pbData, cbData / sizeof(WCHAR), CRYPT_STRING_ANY, pAttr->pbValue, &pAttr->cbValue, NULL, NULL))
|
|
{
|
|
goto DecodeError;
|
|
}
|
|
}
|
|
else if (dwAttrTypeAndAction & CRYPTCAT_ATTR_DATAASCII)
|
|
{
|
|
if (!(pAttr->pbValue = (BYTE *)CatalogNew(cbData)))
|
|
{
|
|
goto ErrorMemory;
|
|
}
|
|
|
|
memcpy(pAttr->pbValue, pbData, cbData);
|
|
pAttr->cbValue = cbData;
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
DWORD pos = 0;
|
|
pAttr = (CRYPTCATATTRIBUTE *) pStack->Get(pos++, NULL);
|
|
while ((pAttr != NULL) && (wcscmp(pAttr->pwszReferenceTag, pwszReferenceTag) != 0))
|
|
{
|
|
pAttr = (CRYPTCATATTRIBUTE *) pStack->Get(pos++, NULL);
|
|
}
|
|
|
|
if (pAttr != NULL)
|
|
{
|
|
DELETE_OBJECT(pAttr->pbValue);
|
|
pAttr->pbValue = NULL;
|
|
pAttr->cbValue = 0;
|
|
|
|
if (!(pAttr->pbValue = (BYTE *)CatalogNew(cbData)))
|
|
{
|
|
goto ErrorMemory;
|
|
}
|
|
|
|
memcpy(pAttr->pbValue, pbData, cbData);
|
|
pAttr->cbValue = cbData;
|
|
}
|
|
}
|
|
|
|
// CommonReturn:
|
|
ErrorReturn:
|
|
return(pAttr);
|
|
|
|
TRACE_ERROR_EX(DBG_SS, StackError);
|
|
TRACE_ERROR_EX(DBG_SS, DecodeError);
|
|
|
|
SET_ERROR_VAR_EX(DBG_SS, ErrorMemory, ERROR_NOT_ENOUGH_MEMORY);
|
|
SET_ERROR_VAR_EX(DBG_SS, ErrorInvalidParam, ERROR_INVALID_PARAMETER);
|
|
}
|
|
|
|
CRYPTCATATTRIBUTE * WINAPI CryptCATEnumerateCatAttr(HANDLE hCatalog, CRYPTCATATTRIBUTE *pPrevAttr)
|
|
{
|
|
CRYPTCATATTRIBUTE *pAttr;
|
|
|
|
pAttr = NULL;
|
|
|
|
if (!(hCatalog) ||
|
|
(hCatalog == (HANDLE)INVALID_HANDLE_VALUE))
|
|
{
|
|
goto ErrorInvalidParam;
|
|
}
|
|
|
|
CRYPTCATSTORE *pStore;
|
|
|
|
pStore = CryptCATStoreFromHandle(hCatalog);
|
|
|
|
if (!(_ISINSTRUCT(CRYPTCATSTORE, pStore->cbStruct, hAttrs)))
|
|
{
|
|
goto ErrorInvalidParam;
|
|
}
|
|
|
|
DWORD dwNext;
|
|
|
|
dwNext = 0;
|
|
|
|
if (pPrevAttr)
|
|
{
|
|
if (!(_ISINSTRUCT(CRYPTCATATTRIBUTE, pPrevAttr->cbStruct, dwReserved)))
|
|
{
|
|
goto ErrorInvalidParam;
|
|
}
|
|
|
|
dwNext = pPrevAttr->dwReserved + 1;
|
|
}
|
|
|
|
if (pStore->hAttrs)
|
|
{
|
|
Stack_ *ps;
|
|
|
|
ps = (Stack_ *)pStore->hAttrs;
|
|
|
|
if (pAttr = (CRYPTCATATTRIBUTE *)ps->Get(dwNext))
|
|
{
|
|
//
|
|
// save our "id" for next time
|
|
//
|
|
pAttr->dwReserved = dwNext;
|
|
|
|
//
|
|
// Done!
|
|
//
|
|
goto CommonReturn;
|
|
}
|
|
}
|
|
|
|
goto ErrorNotFound;
|
|
|
|
CommonReturn:
|
|
ErrorReturn:
|
|
return(pAttr);
|
|
|
|
SET_ERROR_VAR_EX(DBG_SS, ErrorInvalidParam, ERROR_INVALID_PARAMETER);
|
|
SET_ERROR_VAR_EX(DBG_SS, ErrorNotFound, CRYPT_E_NOT_FOUND);
|
|
}
|
|
|
|
CRYPTCATMEMBER * WINAPI CryptCATGetMemberInfo(IN HANDLE hCatalog,
|
|
IN LPWSTR pwszReferenceTag)
|
|
{
|
|
if (!(hCatalog) ||
|
|
(hCatalog == (HANDLE)INVALID_HANDLE_VALUE) ||
|
|
!(pwszReferenceTag))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(NULL);
|
|
}
|
|
|
|
CRYPTCATSTORE *pCatStore;
|
|
CRYPTCATMEMBER *pCatMember;
|
|
|
|
pCatStore = (CRYPTCATSTORE *)hCatalog;
|
|
|
|
if (!(_ISINSTRUCT(CRYPTCATSTORE, pCatStore->cbStruct, hReserved)))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(NULL);
|
|
}
|
|
|
|
pCatMember = NULL;
|
|
|
|
if (pCatStore->hReserved)
|
|
{
|
|
Stack_ *ps;
|
|
|
|
ps = (Stack_ *)pCatStore->hReserved;
|
|
|
|
if (pCatMember = (CRYPTCATMEMBER *)ps->Get(WVT_OFFSETOF(CRYPTCATMEMBER, pwszReferenceTag),
|
|
sizeof(WCHAR *),
|
|
STACK_SORTTYPE_PWSZ,
|
|
pwszReferenceTag))
|
|
{
|
|
if (!(pCatMember->pIndirectData))
|
|
{
|
|
CatalogReallyDecodeIndirectData(pCatStore, pCatMember, &pCatMember->sEncodedIndirectData);
|
|
}
|
|
|
|
if ((pCatMember->gSubjectType.Data1 == 0) &&
|
|
(pCatMember->gSubjectType.Data2 == 0) &&
|
|
(pCatMember->gSubjectType.Data3 == 0))
|
|
{
|
|
CatalogReallyDecodeMemberInfo(pCatStore, pCatMember, &pCatMember->sEncodedMemberInfo);
|
|
}
|
|
|
|
return(pCatMember);
|
|
}
|
|
}
|
|
|
|
return(NULL);
|
|
}
|
|
|
|
|
|
CRYPTCATMEMBER * WINAPI CryptCATPutMemberInfo(HANDLE hCatalog,
|
|
LPWSTR pwszFileName,
|
|
LPWSTR pwszReferenceTag,
|
|
GUID *pgSubjectType,
|
|
DWORD dwCertVersion,
|
|
DWORD cbIndirectData,
|
|
BYTE *pbIndirectData)
|
|
|
|
{
|
|
if (!(hCatalog) ||
|
|
(hCatalog == (HANDLE)INVALID_HANDLE_VALUE) ||
|
|
!(pwszReferenceTag) ||
|
|
!(pgSubjectType) ||
|
|
!(pbIndirectData) ||
|
|
(wcslen(pwszReferenceTag) > CRYPTCAT_MAX_MEMBERTAG))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(NULL);
|
|
}
|
|
|
|
CRYPTCATSTORE *pCatStore;
|
|
|
|
pCatStore = (CRYPTCATSTORE *)hCatalog;
|
|
|
|
if (!(_ISINSTRUCT(CRYPTCATSTORE, pCatStore->cbStruct, hReserved)))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(NULL);
|
|
}
|
|
|
|
Stack_ *pStack;
|
|
CRYPTCATMEMBER *pCatMember;
|
|
|
|
if (!(pCatStore->hReserved))
|
|
{
|
|
pStack = new Stack_(&MSCAT_CriticalSection);
|
|
|
|
if (!(pStack))
|
|
{
|
|
assert(0);
|
|
SetLastError(ERROR_NOT_ENOUGH_MEMORY);
|
|
return(NULL);
|
|
}
|
|
|
|
pCatStore->hReserved = (HANDLE)pStack;
|
|
}
|
|
|
|
//
|
|
// the following is commented out -- too slow!!!!
|
|
//
|
|
// else if (CatalogCheckForDuplicateMember((Stack_ *)pCatStore->hReserved, pwszReferenceTag))
|
|
// {
|
|
// SetLastError(CRYPT_E_EXISTS);
|
|
// return(NULL);
|
|
// }
|
|
|
|
pStack = (Stack_ *)pCatStore->hReserved;
|
|
|
|
if (!(pCatMember = (CRYPTCATMEMBER *)pStack->Add(sizeof(CRYPTCATMEMBER))))
|
|
{
|
|
return(NULL);
|
|
}
|
|
|
|
memset(pCatMember, 0x00, sizeof(CRYPTCATMEMBER));
|
|
|
|
pCatMember->cbStruct = sizeof(CRYPTCATMEMBER);
|
|
|
|
if (pwszFileName)
|
|
{
|
|
if (!(pCatMember->pwszFileName = (LPWSTR)CatalogNew((wcslen(pwszFileName) + 1) *
|
|
sizeof(WCHAR))))
|
|
{
|
|
return(NULL);
|
|
}
|
|
|
|
wcscpy(pCatMember->pwszFileName, pwszFileName);
|
|
}
|
|
|
|
if (!(pCatMember->pwszReferenceTag = (LPWSTR)CatalogNew((wcslen(pwszReferenceTag) + 1) *
|
|
sizeof(WCHAR))))
|
|
{
|
|
return(NULL);
|
|
}
|
|
|
|
wcscpy(pCatMember->pwszReferenceTag, pwszReferenceTag);
|
|
|
|
if (cbIndirectData > 0)
|
|
{
|
|
SIP_INDIRECT_DATA *pInd;
|
|
|
|
if (!(pCatMember->pIndirectData = (SIP_INDIRECT_DATA *)CatalogNew(sizeof(SIP_INDIRECT_DATA))))
|
|
{
|
|
return(NULL);
|
|
}
|
|
|
|
memset(pCatMember->pIndirectData, 0x00, sizeof(SIP_INDIRECT_DATA));
|
|
|
|
pInd = (SIP_INDIRECT_DATA *)pbIndirectData;
|
|
|
|
if (pInd->Data.pszObjId)
|
|
{
|
|
if (!(pCatMember->pIndirectData->Data.pszObjId =
|
|
(LPSTR)CatalogNew(strlen(pInd->Data.pszObjId) + 1)))
|
|
{
|
|
return(NULL);
|
|
}
|
|
|
|
strcpy(pCatMember->pIndirectData->Data.pszObjId, pInd->Data.pszObjId);
|
|
}
|
|
|
|
if (pInd->Data.Value.cbData > 0)
|
|
{
|
|
if (!(pCatMember->pIndirectData->Data.Value.pbData =
|
|
(BYTE *)CatalogNew(pInd->Data.Value.cbData)))
|
|
{
|
|
return(NULL);
|
|
}
|
|
|
|
memcpy(pCatMember->pIndirectData->Data.Value.pbData,
|
|
pInd->Data.Value.pbData, pInd->Data.Value.cbData);
|
|
}
|
|
|
|
pCatMember->pIndirectData->Data.Value.cbData = pInd->Data.Value.cbData;
|
|
|
|
|
|
if (!(pCatMember->pIndirectData->DigestAlgorithm.pszObjId =
|
|
(LPSTR)CatalogNew(strlen(pInd->DigestAlgorithm.pszObjId) + 1)))
|
|
{
|
|
return(NULL);
|
|
}
|
|
strcpy(pCatMember->pIndirectData->DigestAlgorithm.pszObjId,
|
|
pInd->DigestAlgorithm.pszObjId);
|
|
|
|
|
|
if (!(pCatMember->pIndirectData->Digest.pbData =
|
|
(BYTE *)CatalogNew(pInd->Digest.cbData)))
|
|
{
|
|
return(NULL);
|
|
}
|
|
memcpy(pCatMember->pIndirectData->Digest.pbData,
|
|
pInd->Digest.pbData, pInd->Digest.cbData);
|
|
pCatMember->pIndirectData->Digest.cbData = pInd->Digest.cbData;
|
|
}
|
|
|
|
memcpy(&pCatMember->gSubjectType, pgSubjectType, sizeof(GUID));
|
|
|
|
pCatMember->dwCertVersion = dwCertVersion;
|
|
|
|
return(pCatMember);
|
|
}
|
|
|
|
BOOL WINAPI CryptCATVerifyMember(HANDLE hCatalog,
|
|
CRYPTCATMEMBER *pCatMember,
|
|
HANDLE hFileOrMemory)
|
|
{
|
|
if (!(hCatalog) ||
|
|
(hCatalog == (HANDLE)INVALID_HANDLE_VALUE) ||
|
|
!(pCatMember) ||
|
|
!(_ISINSTRUCT(CRYPTCATMEMBER, pCatMember->cbStruct, hReserved)) ||
|
|
!(hFileOrMemory) ||
|
|
(hFileOrMemory == INVALID_HANDLE_VALUE))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(FALSE);
|
|
}
|
|
|
|
CRYPTCATSTORE *pCatStore;
|
|
|
|
pCatStore = (CRYPTCATSTORE *)hCatalog;
|
|
|
|
if (!(_ISINSTRUCT(CRYPTCATSTORE, pCatStore->cbStruct, hReserved)))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(FALSE);
|
|
}
|
|
|
|
// TBDTBD!!!
|
|
|
|
return(FALSE);
|
|
}
|
|
|
|
CRYPTCATATTRIBUTE * WINAPI CryptCATGetAttrInfo(HANDLE hCatalog,
|
|
CRYPTCATMEMBER *pCatMember,
|
|
LPWSTR pwszReferenceTag)
|
|
{
|
|
if (!(hCatalog) ||
|
|
(hCatalog == (HANDLE)INVALID_HANDLE_VALUE) ||
|
|
!(pCatMember) ||
|
|
!(_ISINSTRUCT(CRYPTCATMEMBER, pCatMember->cbStruct, hReserved)) ||
|
|
!(pwszReferenceTag))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(NULL);
|
|
}
|
|
|
|
CRYPTCATSTORE *pCatStore;
|
|
CRYPTCATATTRIBUTE *pCatAttr;
|
|
|
|
pCatStore = (CRYPTCATSTORE *)hCatalog;
|
|
|
|
if (!(_ISINSTRUCT(CRYPTCATSTORE, pCatStore->cbStruct, hReserved)))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(NULL);
|
|
}
|
|
|
|
pCatAttr = NULL;
|
|
|
|
while (pCatAttr = CryptCATEnumerateAttr(hCatalog, pCatMember, pCatAttr))
|
|
{
|
|
if (pCatAttr->pwszReferenceTag)
|
|
{
|
|
if (_wcsicmp(pwszReferenceTag, pCatAttr->pwszReferenceTag) == 0)
|
|
{
|
|
return(pCatAttr);
|
|
}
|
|
}
|
|
}
|
|
|
|
SetLastError(CRYPT_E_NOT_FOUND);
|
|
|
|
return(NULL);
|
|
}
|
|
|
|
|
|
CRYPTCATATTRIBUTE * WINAPI CryptCATPutAttrInfo(HANDLE hCatalog,
|
|
CRYPTCATMEMBER *pCatMember,
|
|
LPWSTR pwszReferenceTag,
|
|
DWORD dwAttrTypeAndAction,
|
|
DWORD cbData,
|
|
BYTE *pbData)
|
|
{
|
|
if (!(hCatalog) ||
|
|
(hCatalog == (HANDLE)INVALID_HANDLE_VALUE) ||
|
|
!(pCatMember) ||
|
|
!(_ISINSTRUCT(CRYPTCATMEMBER, pCatMember->cbStruct, hReserved)) ||
|
|
!(pwszReferenceTag) ||
|
|
((cbData > 0) && !(pbData)))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(NULL);
|
|
}
|
|
|
|
if (!(dwAttrTypeAndAction & CRYPTCAT_ATTR_DATABASE64) &&
|
|
!(dwAttrTypeAndAction & CRYPTCAT_ATTR_DATAASCII))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(NULL);
|
|
}
|
|
|
|
CRYPTCATSTORE *pCatStore;
|
|
|
|
pCatStore = (CRYPTCATSTORE *)hCatalog;
|
|
|
|
if (!(_ISINSTRUCT(CRYPTCATSTORE, pCatStore->cbStruct, hReserved)))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(NULL);
|
|
}
|
|
|
|
Stack_ *pStack;
|
|
CRYPTCATATTRIBUTE *pAttr;
|
|
|
|
if (!(pCatMember->hReserved))
|
|
{
|
|
pStack = new Stack_(&MSCAT_CriticalSection);
|
|
|
|
if (!(pStack))
|
|
{
|
|
assert(0);
|
|
SetLastError(ERROR_NOT_ENOUGH_MEMORY);
|
|
return(NULL);
|
|
}
|
|
|
|
pCatMember->hReserved = (HANDLE)pStack;
|
|
}
|
|
|
|
pStack = (Stack_ *)pCatMember->hReserved;
|
|
|
|
if (!(pAttr = (CRYPTCATATTRIBUTE *)pStack->Add(sizeof(CRYPTCATATTRIBUTE))))
|
|
{
|
|
return(NULL);
|
|
}
|
|
|
|
memset(pAttr, 0x00, sizeof(CRYPTCATATTRIBUTE));
|
|
|
|
pAttr->cbStruct = sizeof(CRYPTCATATTRIBUTE);
|
|
|
|
if (!(pAttr->pwszReferenceTag = (LPWSTR)CatalogNew((wcslen(pwszReferenceTag) + 1) *
|
|
sizeof(WCHAR))))
|
|
{
|
|
return(NULL);
|
|
}
|
|
|
|
wcscpy(pAttr->pwszReferenceTag, pwszReferenceTag);
|
|
|
|
pAttr->dwAttrTypeAndAction = dwAttrTypeAndAction;
|
|
|
|
if (pbData)
|
|
{
|
|
if (dwAttrTypeAndAction & CRYPTCAT_ATTR_DATABASE64)
|
|
{
|
|
CryptStringToBinaryW((WCHAR *)pbData, cbData / sizeof(WCHAR), CRYPT_STRING_ANY, NULL, &pAttr->cbValue, NULL, NULL);
|
|
|
|
if (pAttr->cbValue < 1)
|
|
{
|
|
return(NULL);
|
|
}
|
|
|
|
if (!(pAttr->pbValue = (BYTE *)CatalogNew(pAttr->cbValue)))
|
|
{
|
|
pAttr->cbValue = 0;
|
|
return(NULL);
|
|
}
|
|
|
|
memset(pAttr->pbValue, 0x00, pAttr->cbValue);
|
|
|
|
if (!CryptStringToBinaryW((WCHAR *)pbData, cbData / sizeof(WCHAR), CRYPT_STRING_ANY, pAttr->pbValue, &pAttr->cbValue, NULL, NULL))
|
|
{
|
|
return(NULL);
|
|
}
|
|
}
|
|
else if (dwAttrTypeAndAction & CRYPTCAT_ATTR_DATAASCII)
|
|
{
|
|
if (!(pAttr->pbValue = (BYTE *)CatalogNew(cbData)))
|
|
{
|
|
return(NULL);
|
|
}
|
|
|
|
memcpy(pAttr->pbValue, pbData, cbData);
|
|
pAttr->cbValue = cbData;
|
|
}
|
|
}
|
|
|
|
return(pAttr);
|
|
}
|
|
|
|
|
|
CRYPTCATMEMBER * WINAPI CryptCATEnumerateMember(HANDLE hCatalog,
|
|
CRYPTCATMEMBER *pPrevMember)
|
|
{
|
|
if (!(hCatalog) ||
|
|
(hCatalog == (HANDLE)INVALID_HANDLE_VALUE))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(NULL);
|
|
}
|
|
|
|
CRYPTCATSTORE *pCatStore;
|
|
|
|
pCatStore = (CRYPTCATSTORE *)hCatalog;
|
|
|
|
if (!(_ISINSTRUCT(CRYPTCATSTORE, pCatStore->cbStruct, hReserved)))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(NULL);
|
|
}
|
|
|
|
DWORD dwNext;
|
|
|
|
dwNext = 0;
|
|
|
|
if (pPrevMember)
|
|
{
|
|
if (!(_ISINSTRUCT(CRYPTCATMEMBER, pPrevMember->cbStruct, hReserved)))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(NULL);
|
|
}
|
|
|
|
dwNext = pPrevMember->dwReserved + 1;
|
|
}
|
|
|
|
if (pCatStore->hReserved)
|
|
{
|
|
CRYPTCATMEMBER *pCatMember;
|
|
Stack_ *ps;
|
|
|
|
ps = (Stack_ *)pCatStore->hReserved;
|
|
|
|
if (pCatMember = (CRYPTCATMEMBER *)ps->Get(dwNext))
|
|
{
|
|
//
|
|
// save our "id" for next time
|
|
//
|
|
pCatMember->dwReserved = dwNext;
|
|
|
|
|
|
if (!(pCatMember->pIndirectData))
|
|
{
|
|
CatalogReallyDecodeIndirectData(pCatStore, pCatMember, &pCatMember->sEncodedIndirectData);
|
|
}
|
|
|
|
if ((pCatMember->gSubjectType.Data1 == 0) &&
|
|
(pCatMember->gSubjectType.Data2 == 0) &&
|
|
(pCatMember->gSubjectType.Data3 == 0))
|
|
{
|
|
CatalogReallyDecodeMemberInfo(pCatStore, pCatMember, &pCatMember->sEncodedMemberInfo);
|
|
}
|
|
|
|
//
|
|
// Done!
|
|
//
|
|
return(pCatMember);
|
|
}
|
|
}
|
|
|
|
return(NULL);
|
|
}
|
|
|
|
CRYPTCATATTRIBUTE * WINAPI CryptCATEnumerateAttr(HANDLE hCatalog,
|
|
CRYPTCATMEMBER *pCatMember,
|
|
CRYPTCATATTRIBUTE *pPrevAttr)
|
|
{
|
|
if (!(hCatalog) ||
|
|
(hCatalog == (HANDLE)INVALID_HANDLE_VALUE))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(NULL);
|
|
}
|
|
|
|
CRYPTCATSTORE *pCatStore;
|
|
|
|
pCatStore = (CRYPTCATSTORE *)hCatalog;
|
|
|
|
if (!(_ISINSTRUCT(CRYPTCATSTORE, pCatStore->cbStruct, hReserved)))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(NULL);
|
|
}
|
|
|
|
DWORD dwNext;
|
|
|
|
dwNext = 0;
|
|
|
|
if (pPrevAttr)
|
|
{
|
|
if (!(_ISINSTRUCT(CRYPTCATATTRIBUTE, pPrevAttr->cbStruct, dwReserved)))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(NULL);
|
|
}
|
|
|
|
dwNext = pPrevAttr->dwReserved + 1;
|
|
}
|
|
|
|
if (!(pCatStore) ||
|
|
!(_ISINSTRUCT(CRYPTCATSTORE, pCatStore->cbStruct, hReserved)) ||
|
|
!(pCatMember) ||
|
|
!(_ISINSTRUCT(CRYPTCATMEMBER, pCatMember->cbStruct, hReserved)))
|
|
{
|
|
SetLastError((DWORD)ERROR_INVALID_PARAMETER);
|
|
return(NULL);
|
|
}
|
|
|
|
if (pCatMember->hReserved)
|
|
{
|
|
CRYPTCATATTRIBUTE *pCatAttr;
|
|
Stack_ *ps;
|
|
|
|
ps = (Stack_ *)pCatMember->hReserved;
|
|
|
|
if (pCatAttr = (CRYPTCATATTRIBUTE *)ps->Get(dwNext))
|
|
{
|
|
//
|
|
// save our "id" for next time
|
|
//
|
|
pCatAttr->dwReserved = dwNext;
|
|
|
|
//
|
|
// Done!
|
|
//
|
|
return(pCatAttr);
|
|
}
|
|
}
|
|
|
|
return(NULL);
|
|
}
|
|
|
|
|
|
/////////////////////////////////////////////////////////////////////////////
|
|
//
|
|
// Local Functions
|
|
//
|
|
|
|
BOOL CryptCATCreateStore(CRYPTCATSTORE *pCatStore, LPWSTR pwszCatFile)
|
|
{
|
|
HANDLE hFile;
|
|
DWORD lErr;
|
|
|
|
lErr = GetLastError();
|
|
|
|
if ((hFile = CreateFileU(pwszCatFile,
|
|
GENERIC_WRITE | GENERIC_READ,
|
|
0, // no sharing!!
|
|
NULL,
|
|
CREATE_ALWAYS,
|
|
FILE_ATTRIBUTE_NORMAL,
|
|
NULL)) == INVALID_HANDLE_VALUE)
|
|
{
|
|
return(FALSE);
|
|
}
|
|
|
|
CloseHandle(hFile);
|
|
|
|
SetLastError(lErr);
|
|
|
|
return(CryptCATOpenStore(pCatStore, pwszCatFile));
|
|
}
|
|
|
|
BOOL CryptCATOpenStore(CRYPTCATSTORE *pCatStore, LPWSTR pwszCatFile)
|
|
{
|
|
if (!(pCatStore->pwszP7File = (LPWSTR)CatalogNew((wcslen(pwszCatFile) + 1) *
|
|
sizeof(WCHAR))))
|
|
{
|
|
return(FALSE);
|
|
}
|
|
|
|
wcscpy(pCatStore->pwszP7File, pwszCatFile);
|
|
|
|
return(CatalogLoadFileData(pCatStore));
|
|
}
|