unsigned int RpcVMCAGetServerOption( handle_t IDL_handle, unsigned int *pdwOption ) { DWORD dwError = 0; unsigned int dwOption = 0; if (!pdwOption) { dwError = ERROR_INVALID_PARAMETER; BAIL_ON_VMCA_ERROR(dwError); } dwError = VMCACheckAccess(IDL_handle, TRUE); BAIL_ON_VMCA_ERROR(dwError); dwError = VMCAConfigGetDword(VMCA_REG_KEY_SERVER_OPTION, &dwOption); dwError = dwError == ERROR_FILE_NOT_FOUND ? 0: dwError; BAIL_ON_VMCA_ERROR(dwError); *pdwOption = dwOption; cleanup: VMCA_LOG_DEBUG("Exiting %s, Status = %d", __FUNCTION__, dwError); return dwError; error: goto cleanup; }
DWORD VMCAInitLog() { DWORD dwError = 0; PSTR pszLogDir = NULL; pthread_rwlock_wrlock(&rwloglock); VMCAReadLogConfig(); if (gVMCALogType == VMCA_LOG_TYPE_FILE) { dwError = VMCAGetLogFileDirectory(&pszLogDir); BAIL_ON_VMCA_ERROR(dwError); dwError = VMCARenameLogs(); BAIL_ON_VMCA_ERROR(dwError); dwError = VMCACreatePrimaryLog(pszLogDir); BAIL_ON_VMCA_ERROR(dwError); } #ifndef WIN32 if (gVMCALogType == VMCA_LOG_TYPE_SYSLOG) { openlog("vmcad", 0, LOG_DAEMON); } #endif error : pthread_rwlock_unlock(&rwloglock); VMCA_SAFE_FREE_STRINGA(pszLogDir); return dwError; }
DWORD VMCAAllocateStringW( PCWSTR pwszSrc, PWSTR* ppwszDst ) { DWORD dwError = 0; if (!pwszSrc || !ppwszDst) { dwError = ERROR_INVALID_PARAMETER; } else { #ifdef _WIN32 PWSTR pwszNewString = NULL; size_t len = wcslen(pwszSrc); dwError = VMCAAllocateMemory( (DWORD) (len + 1)*sizeof(WCHAR), (PVOID *)&pwszNewString ); BAIL_ON_VMCA_ERROR(dwError); wcscpy_s(pwszNewString, (len + 1), pwszSrc); *ppwszDst = pwszNewString; #else dwError = LwNtStatusToWin32Error( LwRtlWC16StringDuplicate(ppwszDst, pwszSrc)); BAIL_ON_VMCA_ERROR(dwError); #endif } error: return dwError; }
unsigned int RpcVMCAUnsetServerOption( handle_t IDL_handle, unsigned int dwOption ) { DWORD dwError = 0; unsigned int dwCurrentOption = 0; unsigned int dwNewOption = 0; dwError = VMCACheckAccess(IDL_handle, TRUE); BAIL_ON_VMCA_ERROR(dwError); dwError = VMCAConfigGetDword(VMCA_REG_KEY_SERVER_OPTION, &dwCurrentOption); dwError = dwError == ERROR_FILE_NOT_FOUND ? 0: dwError; BAIL_ON_VMCA_ERROR(dwError); dwNewOption = dwCurrentOption & ~dwOption; dwError = VMCAConfigSetDword(VMCA_REG_KEY_SERVER_OPTION, dwNewOption); BAIL_ON_VMCA_ERROR(dwError); cleanup: VMCA_LOG_DEBUG("Exiting %s, Status = %d", __FUNCTION__, dwError); return dwError; error: goto cleanup; }
static DWORD InitializeRPCServer( VOID ) { DWORD dwError = 0; dwError = VMCAStartRpcServer(); BAIL_ON_VMCA_ERROR(dwError); dwError = dcethread_create( &gVMCAServerGlobals.pRPCServerThread, NULL, VMCAListenRpcServer, NULL); dwError = VMCAMapDCEErrorCode(dwError); BAIL_ON_VMCA_ERROR(dwError); while (!VMCACheckRPCServerIsActive()) { // Wait for RPC Server to come up. VMCASleep(1); } error: return dwError; }
static VOID VMCAShutdownRPCServer( VOID ) { DWORD dwError = 0; // stop rpc listening dwError = VMCAStopRpcServer(); BAIL_ON_VMCA_ERROR(dwError); if (gVMCAServerGlobals.pRPCServerThread) { dwError = dcethread_interrupt(gVMCAServerGlobals.pRPCServerThread); dwError = VMCAMapDCEErrorCode(dwError); BAIL_ON_VMCA_ERROR(dwError); #if defined(_WIN32) // BUGBUG BUGBUG PR http://bugzilla.eng.vmware.com/show_bug.cgi?id=1219191 // This is most likely a pthread issue due to signal lost. // We should update pthread to see if we can resolve this. // http://bugzilla.eng.vmware.com/show_bug.cgi?id=1224401 tracks this effort. VMCASleep(1); // sleep 1s #else dwError = dcethread_join(gVMCAServerGlobals.pRPCServerThread, NULL); dwError = VMCAMapDCEErrorCode(dwError); BAIL_ON_VMCA_ERROR(dwError); #endif gVMCAServerGlobals.pRPCServerThread = NULL; } error: return; }
static DWORD InitializeDatabase( VOID ) { DWORD dwError = 0 ; PSTR pszCertDBPath = NULL; dwError = VMCACreateDataDirectory(); BAIL_ON_VMCA_ERROR(dwError); dwError = VMCAGetCertsDBPath(&pszCertDBPath); BAIL_ON_VMCA_ERROR(dwError); VMCA_LOG_INFO( "Initializing database: [%s]", VMCA_SAFE_STRING(pszCertDBPath)); dwError = VmcaDbInitialize(pszCertDBPath); BAIL_ON_VMCA_ERROR(dwError); error: VMCA_SAFE_FREE_STRINGA(pszCertDBPath); return dwError; }
uint32_t make_negotiate_token( gss_buffer_desc *pBuffer, char **ppszNegotiate ) { uint32_t dwError = 0; char *pszEncodedData = NULL; char *pszNegotiate = NULL; //int len = 0; if (pBuffer) { dwError = base64_encode( pBuffer->value, pBuffer->length, &pszEncodedData); BAIL_ON_VMCA_ERROR(dwError); } dwError = VMCAAllocateStringPrintfA( &pszNegotiate, "Negotiate %s", pszEncodedData ? pszEncodedData : ""); BAIL_ON_VMCA_ERROR(dwError); *ppszNegotiate = pszNegotiate; cleanup: VMCA_SAFE_FREE_MEMORY(pszEncodedData); return dwError; error: VMCA_SAFE_FREE_MEMORY(pszNegotiate); goto cleanup; }
DWORD VMCACreatePrimaryLog(PSTR pszLogDir) { DWORD dwError = 0; PSTR pszDestFile = NULL; if(pszLogDir == NULL) { dwError = ERROR_INVALID_PARAMETER; BAIL_ON_VMCA_ERROR(dwError); } dwError = VMCAAllocateStringPrintfA( &pszDestFile, FORMATSTR, pszLogDir, VMCA_LOG_STRING, 0);// This is always the Current Log File BAIL_ON_VMCA_ERROR(dwError); if (fpCurrentLog != NULL) { fclose(fpCurrentLog); fpCurrentLog = NULL; } fpCurrentLog = fopen(pszDestFile, "a"); gVMCACurrentLogSizeBytes = 0; error : VMCA_SAFE_FREE_STRINGA(pszDestFile); return dwError; }
unsigned int RpcVMCARevokeCertificate( handle_t IDL_handle, unsigned char *pszCertificate, wchar16_t *pszSharedSecret) { DWORD dwError = 0; VMCA_LOG_DEBUG("Entering %s", __FUNCTION__); dwError = VMCACheckAccess(IDL_handle, TRUE); BAIL_ON_VMCA_ERROR(dwError); if(pszCertificate == NULL) { dwError = ERROR_INVALID_PARAMETER; BAIL_ON_VMCA_ERROR(dwError); } dwError = VMCARevokeCertificate(pszCertificate); BAIL_ON_VMCA_ERROR(dwError); cleanup: VMCA_LOG_DEBUG("Exiting %s, Status = %d", __FUNCTION__, dwError); return dwError; error: goto cleanup; }
DWORD VMCAReadDataFromFile( PSTR pszFileName, DWORD dwOffset, DWORD dwSize, PSTR data, PDWORD dwBytesRead) { DWORD dwError = 0; FILE *pFile = NULL; int bytes_read = 0; dwError = VMCAOpenFilePath(pszFileName, "r", &pFile); BAIL_ON_VMCA_ERROR(dwError); if ( pFile == NULL) { dwError = VMCA_FILE_IO_ERROR; BAIL_ON_VMCA_ERROR(dwError); } dwError = fseek(pFile, dwOffset, SEEK_SET); BAIL_ON_VMCA_ERROR(dwError); bytes_read = fread(data, 1, dwSize, pFile); if ( !feof(pFile) && ( bytes_read != dwSize)){ dwError = VMCA_FILE_IO_ERROR; BAIL_ON_VMCA_ERROR(dwError); } *dwBytesRead = bytes_read; error : if(pFile != NULL){ fclose(pFile); } return dwError; }
unsigned int VMCAReGenCRL() { DWORD dwError = 0; PSTR pszTmpFile = NULL; DWORD dwExists = 0; dwError = VMCAGetTempCRLNamePath(&pszTmpFile); BAIL_ON_VMCA_ERROR(dwError); dwError = VMCACheckFileExists(pszTmpFile,&dwExists); if(dwExists == FILE_EXISTS) { dwError = remove(pszTmpFile); if ( dwError == -1) { dwError = VMCA_FILE_REMOVE_ERROR; } BAIL_ON_VMCA_ERROR(dwError); } dwError = VMCAGenerateCRL(); BAIL_ON_VMCA_ERROR(dwError); dwError = VMCACopyTempCRLtoCRL(); BAIL_ON_VMCA_ERROR(dwError); error : VMCA_SAFE_FREE_STRINGA(pszTmpFile); return dwError; }
unsigned int RpcVMCAGetSignedCertificate( handle_t IDL_handle, unsigned char *pszPEMEncodedCSRRequest, unsigned int dwValidFrom, unsigned int dwDurationInSeconds, wchar16_t *pszSharedSecret, unsigned int *pdwCertLength, VMCA_CERTIFICATE_CONTAINER **ppCertContainer) { DWORD dwError = 0; VMCA_CERTIFICATE_CONTAINER* pCertContainer = NULL; VMCA_CERTIFICATE_CONTAINER* pTempCertContainer = NULL; VMCA_LOG_DEBUG("Entering %s", __FUNCTION__); if (ppCertContainer == NULL || pszPEMEncodedCSRRequest == NULL) { dwError = ERROR_INVALID_PARAMETER; BAIL_ON_VMCA_ERROR(dwError); } dwError = VMCACheckAccess(IDL_handle, FALSE); BAIL_ON_VMCA_ERROR(dwError); dwError = VMCAGetSignedCertificate( pszPEMEncodedCSRRequest, dwValidFrom, dwDurationInSeconds, &pTempCertContainer); BAIL_ON_VMCA_ERROR(dwError); dwError = VMCARpcAllocateCertificateContainer( pTempCertContainer->pCert, &pCertContainer); BAIL_ON_VMCA_ERROR(dwError); strcpy((char*)pCertContainer->pCert, (char*)pTempCertContainer->pCert); *ppCertContainer = pCertContainer; cleanup: VMCAFreeCertificateContainer (pTempCertContainer); VMCA_LOG_DEBUG("Exiting %s, Status = %d", __FUNCTION__, dwError); return dwError; error: if (pdwCertLength) { *pdwCertLength = 0; } if (ppCertContainer) { *ppCertContainer = NULL; } VMCARpcFreeCertificateContainer(pCertContainer); goto cleanup; }
unsigned int RpcVMCAEnumCertificates( handle_t IDL_handle, CERTIFICATE_STATUS dwStatus, unsigned int dwStartIndex, unsigned int dwNumCertificates, VMCA_CERTIFICATE_ARRAY** ppCertArray) { DWORD dwError = 0; VMCA_CERTIFICATE_ARRAY* pTempCertArray = NULL; VMCA_CERTIFICATE_ARRAY* pCertArray = NULL; VMCA_LOG_DEBUG("Entering %s", __FUNCTION__); if (ppCertArray == NULL) { dwError = ERROR_INVALID_PARAMETER; BAIL_ON_VMCA_ERROR(dwError); } dwError = VMCACheckAccess(IDL_handle, TRUE); BAIL_ON_VMCA_ERROR(dwError); dwError = VMCAEnumCertificates( dwStartIndex, dwNumCertificates, dwStatus, &pTempCertArray); BAIL_ON_VMCA_ERROR(dwError); dwError = RpcVMCACopyCertificateToRPC( pTempCertArray, &pCertArray); BAIL_ON_VMCA_ERROR(dwError); *ppCertArray = pCertArray; cleanup: if (pTempCertArray) { VMCAFreeCertificateArray(pTempCertArray); } VMCA_LOG_DEBUG("Exiting %s, Status = %d", __FUNCTION__, dwError); return dwError; error: if (ppCertArray) { *ppCertArray = NULL; } if (pCertArray) { VMCARpcFreeCertificateArray(pCertArray); } goto cleanup; }
DWORD VmcaDbCreateContext( PVMCA_DB_CONTEXT* ppDbContext ) { DWORD dwError = 0; PVMCA_DB_CONTEXT pDbContext = NULL; BOOLEAN bInLock = FALSE; VMCA_LOG_(VMCA_LOG_LEVEL_DEBUG,"Creating VMCA database context"); VMCA_LOCK_MUTEX(bInLock, &gVmcaDbGlobals.mutex); if (gVmcaDbGlobals.pDbContextList) { pDbContext = gVmcaDbGlobals.pDbContextList; gVmcaDbGlobals.pDbContextList = gVmcaDbGlobals.pDbContextList->pNext; pDbContext->pNext = NULL; gVmcaDbGlobals.dwNumCachedContexts--; } else { VMCA_LOG_DEBUG("Allocating database context for %s", gVmcaDbGlobals.pszDbPath); dwError = VMCAAllocateMemory(sizeof(*pDbContext), (PVOID*)&pDbContext); BAIL_ON_VMCA_ERROR(dwError); dwError = sqlite3_open( gVmcaDbGlobals.pszDbPath, &pDbContext->pDb); BAIL_ON_VMCA_ERROR(dwError); dwError = sqlite3_busy_timeout( pDbContext->pDb, 5000); BAIL_ON_VMCA_ERROR(dwError); } *ppDbContext = pDbContext; cleanup: VMCA_UNLOCK_MUTEX(bInLock, &gVmcaDbGlobals.mutex); VMCA_LOG_DEBUG("VMCA database context created Error = %d", dwError); return dwError; error: *ppDbContext = NULL; if (pDbContext) { VmcaDbFreeContext(pDbContext); } goto cleanup; }
unsigned int RpcVMCAGetServerVersion( handle_t IDL_handle, unsigned int *pdwCertLength, VMCA_CERTIFICATE_CONTAINER **pServerVersion) { DWORD dwError = 0; PSTR pTempServerVersion = NULL; VMCA_CERTIFICATE_CONTAINER *pTempVersion = NULL; /* * TBD: Probably don't care if this is accessable remotely * Currently VMCA API wiki states this should be SRP authenticated. (??) */ dwError = VMCACheckAccess(IDL_handle, FALSE); BAIL_ON_VMCA_ERROR(dwError); VMCA_LOG_DEBUG("Entering %s", __FUNCTION__); if (pServerVersion == NULL) { dwError = ERROR_INVALID_PARAMETER; BAIL_ON_VMCA_ERROR(dwError); } dwError = VMCAGetServerVersion(&pTempServerVersion); BAIL_ON_VMCA_ERROR(dwError); dwError = VMCARpcAllocateCertificateContainer (pTempServerVersion, &pTempVersion); BAIL_ON_VMCA_ERROR(dwError); strcpy(pTempVersion->pCert,pTempServerVersion); *pServerVersion = pTempVersion; cleanup: VMCA_SAFE_FREE_STRINGA(pTempServerVersion); VMCA_LOG_DEBUG("Exiting %s, Status = %d", __FUNCTION__, dwError); return dwError; error: if(pdwCertLength) { *pdwCertLength = 0; } if (pServerVersion) { *pServerVersion = NULL; } if (pTempVersion) { VMCARpcFreeCertificateContainer(pTempVersion); pTempVersion = NULL; } goto cleanup; }
// db entry util unsigned int VMCACloneCertContainerFromDbCertEntryArray( PVMCA_DB_CERTIFICATE_ENTRY pDbCertEntryArray, DWORD dwDbCertEntryNums, VMCA_CERTIFICATE_ARRAY** ppCertArray ) { DWORD dwError = 0; PVMCA_CERTIFICATE_ARRAY pCertArray = NULL; dwError = VMCARpcAllocateMemory( sizeof(VMCA_CERTIFICATE_ARRAY), (PVOID*)&pCertArray); BAIL_ON_VMCA_ERROR(dwError); // get array size pCertArray->dwCount = dwDbCertEntryNums; if (pCertArray->dwCount > 0) { DWORD iEntry = 0; dwError = VMCARpcAllocateMemory( pCertArray->dwCount * sizeof(pCertArray->certificates[0]), (PVOID*)&pCertArray->certificates); BAIL_ON_VMCA_ERROR(dwError); for (; iEntry < pCertArray->dwCount; iEntry++) { PVMCA_DB_CERTIFICATE_ENTRY pDbCertEntrySrc = &pDbCertEntryArray[iEntry]; PVMCA_CERTIFICATE_CONTAINER pCertContainerDst = &pCertArray->certificates[iEntry]; // copy pCert string to container dwError = VMCAClonePkgEntryContentsFromDbPkgEntry( pDbCertEntrySrc, pCertContainerDst); BAIL_ON_VMCA_ERROR(dwError); } } *ppCertArray = pCertArray; cleanup: return dwError; error: *ppCertArray = NULL; if (pCertArray) { VMCARpcFreeCertificateArray(pCertArray); } goto cleanup; }
DWORD VMCARestServerInit( VOID ) { DWORD dwError = 0; MODULE_REG_MAP stRegMap[] = { //{"endpoint", VMCARestFunctionModule}, {NULL, NULL} }; /* * We can use the same REST_API_SPEC for both HTTP and HTTPS * if the rest init code refers to common API definitions */ dwError = coapi_load_from_file(REST_API_SPEC, &gpVMCARestApiDef); BAIL_ON_VMCA_ERROR(dwError); dwError = coapi_map_api_impl(gpVMCARestApiDef, stRegMap); BAIL_ON_VMCA_ERROR(dwError); dwError = VMCAOpensslInit(); BAIL_ON_VMCA_ERROR(dwError); dwError = _VMCARestServerInitHTTPS(); if (dwError != 0) { /* * Before promoting lightwave node, obtaining cert from VECS will fail which is expected * hence treat it as soft fail */ VMCA_LOG_WARNING( "VmRESTServerInit: HTTPS port init failed with error %d, (failure is expected before promote)", dwError); dwError = 0; } cleanup: return dwError; error: if (VMCARestServerStop() == 0) { VMCARestServerShutdown(); } VMCA_LOG_ERROR( "%s failed, error (%d)", __FUNCTION__, dwError); goto cleanup; }
DWORD VMCACreateDirectory(PSTR pszDirectoryName, BOOL bRestrictAccess) { DWORD dwError = 0; PSTR pszDir = NULL; #ifdef _WIN32 PSTR pszTemp = NULL; int err = 0; #endif if (!pszDirectoryName || !*pszDirectoryName) { dwError = ERROR_INVALID_PARAMETER; BAIL_ON_VMCA_ERROR(dwError); } #ifndef _WIN32 mkdir(pszDirectoryName, 700); goto error; #else dwError = VMCAAllocateStringA(pszDirectoryName, &pszDir); BAIL_ON_VMCA_ERROR(dwError); pszTemp = pszDir; if (strlen(pszDir) > 3 && pszDir[1] == ':' && pszDir[2] == '\\') { pszTemp += 3; } while ( (pszTemp = strchr(pszTemp, '\\')) ) { *pszTemp = '\0'; err = _mkdir(pszDir); if(err == -1 && errno != EEXIST) { dwError = ERROR_PATH_NOT_FOUND; BAIL_ON_VMCA_ERROR(dwError); } *pszTemp++ = '/'; } if (bRestrictAccess) { dwError = VMCARestrictDirectoryAccess(pszDir); BAIL_ON_VMCA_ERROR(dwError); } #endif error: VMCA_SAFE_FREE_STRINGA(pszDir); return dwError; }
DWORD RpcVMCACopyCertificateToRPC( VMCA_CERTIFICATE_ARRAY* pInputCertArray, VMCA_CERTIFICATE_ARRAY** pOutputCertArray ) { DWORD dwError = 0; VMCA_CERTIFICATE_ARRAY* pCertArray = NULL; dwError = VMCARpcAllocateMemory( sizeof(VMCA_CERTIFICATE_ARRAY), (PVOID*)&pCertArray); BAIL_ON_VMCA_ERROR(dwError); pCertArray->dwCount = pInputCertArray->dwCount; if (pCertArray->dwCount > 0) { DWORD iEntry = 0; dwError = VMCARpcAllocateMemory( pCertArray->dwCount * sizeof(pCertArray->certificates[0]), (PVOID*)&pCertArray->certificates); BAIL_ON_VMCA_ERROR(dwError); for (; iEntry < pCertArray->dwCount; iEntry++) { pCertArray->certificates[iEntry].dwCount = pInputCertArray->certificates[iEntry].dwCount; dwError = VMCARpcAllocateString( (RP_PSTR)pInputCertArray->certificates[iEntry].pCert, (RP_PSTR*)&pCertArray->certificates[iEntry].pCert); BAIL_ON_VMCA_ERROR(dwError); } } *pOutputCertArray = pCertArray; cleanup: return dwError; error: if (pCertArray) { VMCARpcFreeCertificateArray(pCertArray); } goto cleanup; }
DWORD VMCACheckAccess( handle_t IDL_handle, BOOL bNeedAdminPrivilage ) { DWORD dwError = 0; rpc_authz_cred_handle_t hPriv = { 0 }; DWORD dwProtectLevel = 0; ULONG rpc_status = rpc_s_ok; unsigned char *authPrinc = NULL; rpc_binding_inq_auth_caller( IDL_handle, &hPriv, &authPrinc, &dwProtectLevel, NULL, /* unsigned32 *authn_svc, */ NULL, /* unsigned32 *authz_svc, */ &rpc_status); /* Deny if connection is not encrypted */ if (dwProtectLevel < rpc_c_protect_level_pkt_privacy) { dwError = VMCA_KRB_ACCESS_DENIED; BAIL_ON_VMCA_ERROR(dwError); } /* Deny if no auth identity is provided. */ if (rpc_status == rpc_s_binding_has_no_auth || !authPrinc || !*authPrinc) { dwError = VMCA_KRB_ACCESS_DENIED; BAIL_ON_VMCA_ERROR(dwError); } VMCA_LOG_INFO("VMCACheckAccessKrb: Authenticated user %s", authPrinc); if (bNeedAdminPrivilage) { dwError = VMCALdapAccessCheck(authPrinc, VMCA_ADMINISTRATORS); BAIL_ON_VMCA_ERROR(dwError); } error: if (authPrinc) { rpc_string_free((unsigned_char_t **)&authPrinc, &rpc_status); } return dwError; }
DWORD VMCASrvDirSyncInit( VOID ) { DWORD dwError = 0; PVMCA_THREAD pThread = NULL; BOOLEAN bLocked = FALSE; PVMCA_DIR_SYNC_PARAMS pDirSyncParams = NULL; DWORD dwSyncInterval = 5 * 60 * 60; // every 5 minutes dwError = VMCASrvCreateDirSyncParams(dwSyncInterval, &pDirSyncParams); BAIL_ON_VMCA_ERROR(dwError); VMCA_LOCK_MUTEX(bLocked, &gVMCAServerGlobals.mutex); gVMCAServerGlobals.pDirSyncParams = VMCASrvAcquireDirSyncParams( pDirSyncParams); VMCA_UNLOCK_MUTEX(bLocked, &gVMCAServerGlobals.mutex); dwError = VMCACreateThread( &VMCASrvDirSyncThrFunc, pDirSyncParams, &pThread); BAIL_ON_VMCA_ERROR(dwError); VMCA_LOCK_MUTEX(bLocked, &gVMCAServerGlobals.mutex); gVMCAServerGlobals.pDirSyncThr = VMCAAcquireThread(pThread); cleanup: VMCA_UNLOCK_MUTEX(bLocked, &gVMCAServerGlobals.mutex); if (pDirSyncParams) { VMCASrvReleaseDirSyncParams(pDirSyncParams); } if (pThread) { VMCAReleaseThread(pThread); } return dwError; error: goto cleanup; }
DWORD VMCAVerifyCertificate( unsigned char *pszPEMEncodedCertificate, unsigned int *dwStatus ) { DWORD dwError = 0; PVMCA_DB_CERTIFICATE_ENTRY pEntry = NULL; PVMCA_DB_CONTEXT pContext = NULL; BOOLEAN bLocked = FALSE; *dwStatus = VMCA_CERTIFICATE_ALL; VMCA_LOCK_MUTEX_SHARED(&gVMCAServerGlobals.svcMutex, bLocked); dwError = VMCASrvValidateCA(); BAIL_ON_VMCA_ERROR(dwError); dwError = VMCADecodeCert((LPSTR)pszPEMEncodedCertificate, &pEntry); BAIL_ON_VMCA_ERROR(dwError); if (pEntry->dwRevoked == VMCA_CERTIFICATE_EXPIRED) { *dwStatus = VMCA_CERTIFICATE_EXPIRED; goto error; } dwError = VmcaDbCreateContext(&pContext); BAIL_ON_VMCA_ERROR(dwError); dwError = VmcaDbVerifyCertificate(pContext, pEntry->pwszSerial, (DWORD*)dwStatus); BAIL_ON_VMCA_ERROR(dwError); error : VMCA_LOCK_MUTEX_UNLOCK(&gVMCAServerGlobals.svcMutex, bLocked); if (pContext != NULL) { VmcaDbReleaseContext(pContext); pContext = NULL; } if(pEntry != NULL) { VMCAFreeDBEntryFields(pEntry); pEntry = NULL; } return dwError; }
DWORD _VMCAMkDir( PSTR pszDirName, int mode) { DWORD dwError = 0; #ifdef _WIN32 UNUSED(mode); dwError = _mkdir(pszDirName); BAIL_ON_VMCA_ERROR(dwError); #else dwError = mkdir(pszDirName, mode); BAIL_ON_VMCA_ERROR(dwError); #endif error: return dwError; }
DWORD VMCARESTGetPayload( PVMREST_HANDLE pRESTHandle, PREST_REQUEST pRESTRequest, VMCA_HTTP_REQ_OBJ* pVMCARequest ) { DWORD dwError = 0; DWORD bytesRead = 0; size_t len = 0; PSTR pszPayload = NULL; do { if (bytesRead || !pszPayload) { dwError = VMCAReallocateMemory( (PVOID)pszPayload, (PVOID*)&pszPayload, len + VMCARESTMAXPAYLOADLENGTH + 1); // +1 for NULL char BAIL_ON_VMCA_ERROR(dwError); } bytesRead = 0; dwError = VmRESTGetData( pRESTHandle, pRESTRequest, pszPayload + len, &bytesRead); len += bytesRead; } while (dwError == REST_ENGINE_MORE_IO_REQUIRED); BAIL_ON_VMCA_ERROR(dwError); pszPayload[len] = 0; pVMCARequest->pszPayload = pszPayload; pszPayload = NULL; cleanup: VMCA_SAFE_FREE_MEMORY(pszPayload); return dwError; error: goto cleanup; }
static DWORD VMCASrvCreateDirSyncParams( DWORD dwInterval, PVMCA_DIR_SYNC_PARAMS* ppSyncInfo ) { DWORD dwError = 0; PVMCA_DIR_SYNC_PARAMS pSyncInfo = NULL; dwError = VMCAAllocateMemory( sizeof(VMCA_DIR_SYNC_PARAMS), (PVOID*)&pSyncInfo); BAIL_ON_VMCA_ERROR(dwError); pSyncInfo->refCount = 1; dwError = pthread_mutex_init(&pSyncInfo->mutex, NULL); if (dwError) { #ifndef _WIN32 dwError = LwErrnoToWin32Error(dwError); #endif BAIL_ON_VMCA_ERROR(dwError); } pSyncInfo->pMutex = &pSyncInfo->mutex; pSyncInfo->dwSyncIntervalSecs = dwInterval; *ppSyncInfo = pSyncInfo; cleanup: return dwError; error: *ppSyncInfo = NULL; if (pSyncInfo) { VMCASrvReleaseDirSyncParams(pSyncInfo); } goto cleanup; }
DWORD VMCARpcAllocateStringW( RP_PWSTR pwszSrc, RP_PWSTR* ppwszDst ) { DWORD dwError = 0; size_t len = 0; RP_PWSTR pwszDst = NULL; if (!pwszSrc || !ppwszDst) { dwError = ERROR_INVALID_PARAMETER; BAIL_ON_VMCA_ERROR(dwError); } dwError = LwWc16sLen(pwszSrc, &len); BAIL_ON_VMCA_ERROR(dwError); dwError = VMCARpcAllocateMemory( sizeof(RP_WSTR) * (len + 1), (PVOID*)&pwszDst); BAIL_ON_VMCA_ERROR(dwError); dwError = LwWc16snCpy(pwszDst, pwszSrc, len); BAIL_ON_VMCA_ERROR(dwError); *ppwszDst = pwszDst; cleanup: return dwError; error: if (ppwszDst) { *ppwszDst = NULL; } if (pwszDst) { VMCARpcFreeMemory(pwszDst); } goto cleanup; }
unsigned int VMCAGetRootCACertificate( unsigned int *dwCertLength, VMCA_CERTIFICATE_CONTAINER **ppCertContainer ) { DWORD dwError = 0; PVMCA_CERTIFICATE pCertificate = NULL; PSTR pszRootCertFile = NULL; BOOLEAN bLocked = FALSE; VMCA_LOCK_MUTEX_SHARED(&gVMCAServerGlobals.svcMutex, bLocked); dwError = VMCASrvValidateCA(); BAIL_ON_VMCA_ERROR(dwError); VMCAGetRootCertificateFilePath(&pszRootCertFile); BAIL_ON_VMCA_ERROR(dwError); dwError = VMCAReadCertificateChainFromFile( pszRootCertFile, &pCertificate); BAIL_ON_VMCA_ERROR(dwError); dwError = VMCARpcAllocateCertificateContainer(pCertificate, ppCertContainer); BAIL_ON_VMCA_ERROR(dwError); strcpy((char*)(*ppCertContainer)->pCert,pCertificate); error : VMCA_LOCK_MUTEX_UNLOCK(&gVMCAServerGlobals.svcMutex, bLocked); if( dwError != 0) { if (ppCertContainer && *ppCertContainer) { VMCARpcFreeCertificateContainer(*ppCertContainer); *ppCertContainer = NULL; } } VMCA_SAFE_FREE_STRINGA(pCertificate); VMCA_SAFE_FREE_STRINGA(pszRootCertFile); pCertificate = NULL; return dwError; }
DWORD VMCASrvPublishRootCerts( VOID ) { DWORD dwError = 0; dwError = VMCASrvValidateCA(); BAIL_ON_VMCA_ERROR(dwError); dwError = VMCASrvNotifyDirSync(); BAIL_ON_VMCA_ERROR(dwError); error: return dwError; }
DWORD VMCAUpdateAuthorityKeyIdentifier( X509_CRL *pCrl, PVMCA_X509_CA pCA ) { DWORD dwError = 0; X509V3_CTX ctx; X509_EXTENSION *pExtension = NULL; if (!pCA || !pCA->pCertificate || !pCrl ) { dwError = ERROR_INVALID_PARAMETER; BAIL_ON_VMCA_ERROR (dwError); } X509V3_set_ctx_nodb (&ctx); X509V3_set_ctx( &ctx, pCA->pCertificate, NULL, NULL, pCrl, 0 ); pExtension = X509V3_EXT_conf_nid( NULL, &ctx, NID_authority_key_identifier, "keyid" ); if (!pExtension) { goto error; } X509_CRL_add_ext (pCrl, pExtension, -1); cleanup: if (pExtension) { X509_EXTENSION_free(pExtension); } return dwError; error: goto cleanup; }