VOID RegPrintError( IN OPTIONAL PCSTR pszErrorPrefix, IN DWORD dwError ) { PCSTR pszUseErrorPrefix = NULL; size_t size = 0; PSTR pszErrorString = NULL; PCSTR pszWinError = NULL; if (dwError) { pszUseErrorPrefix = pszErrorPrefix; if (!pszUseErrorPrefix) { pszUseErrorPrefix = "LWREG ERROR: "; } size = LwRegGetErrorString(dwError, NULL, 0); if (size) { pszErrorString = malloc(size); if (pszErrorString) { LwRegGetErrorString(dwError, pszErrorString, size); } } pszWinError = LW_PRINTF_STRING(RegWin32ExtErrorToName(dwError)); if (!pszWinError) { pszWinError = ""; } if (LW_IS_NULL_OR_EMPTY_STR(pszErrorString)) { fprintf(stderr, "%s (error = %u%s%s)\n", pszUseErrorPrefix, dwError, *pszWinError ? " - " : "", pszWinError); } else { fprintf(stderr, "%s (error = %u%s%s)\n%s\n", pszUseErrorPrefix, dwError, *pszWinError ? " - " : "", pszWinError, pszErrorString); } } LWREG_SAFE_FREE_STRING(pszErrorString); }
DWORD RegGetErrorMessageForLoggingEvent( DWORD dwErrCode, PSTR* ppszErrorMsg ) { DWORD dwErrorBufferSize = 0; DWORD dwError = 0; DWORD dwLen = 0; PSTR pszErrorMsg = NULL; PSTR pszErrorBuffer = NULL; dwErrorBufferSize = LwRegGetErrorString(dwErrCode, NULL, 0); if (!dwErrorBufferSize) goto cleanup; dwError = LW_RTL_ALLOCATE((PVOID*)&pszErrorBuffer, CHAR, sizeof(*pszErrorBuffer) * dwErrorBufferSize); BAIL_ON_REG_ERROR(dwError); dwLen = LwRegGetErrorString(dwErrCode, pszErrorBuffer, dwErrorBufferSize); if ((dwLen == dwErrorBufferSize) && !IsNullOrEmptyString(pszErrorBuffer)) { dwError = RegCStringAllocatePrintf( &pszErrorMsg, "Error: %s [error code: %d]", pszErrorBuffer, dwErrCode); BAIL_ON_REG_ERROR(dwError); } *ppszErrorMsg = pszErrorMsg; cleanup: LWREG_SAFE_FREE_STRING(pszErrorBuffer); return dwError; error: LWREG_SAFE_FREE_STRING(pszErrorMsg); *ppszErrorMsg = NULL; goto cleanup; }
PVOID UmnSrvPollerThreadRoutine( IN PVOID pUnused ) { DWORD dwError = 0; struct timeval now; struct timespec periodStart, periodUsed, nextWake, pushWait = {0}; DWORD dwPeriodSecs = 0; char regErrMsg[256] = {0}; char fqdn[1024] = {0}; BOOLEAN bMutexLocked = FALSE; UMN_LOG_INFO("User poller thread started"); dwError = pthread_mutex_lock(&gSignalPollerMutex); BAIL_ON_UMN_ERROR(dwError); bMutexLocked = TRUE; dwError = UmnSrvNow(&periodStart, &now); BAIL_ON_UMN_ERROR(dwError); while (!gbPollerThreadShouldExit) { dwError = UmnSrvGetCheckInterval(&dwPeriodSecs); BAIL_ON_UMN_ERROR(dwError); pushWait.tv_sec = dwPeriodSecs; UmnSrvTimespecAdd( &nextWake, &periodStart, &pushWait); UMN_LOG_INFO("User poller sleeping for %f seconds", pushWait.tv_sec + pushWait.tv_nsec / (double)NANOSECS_PER_SECOND); while (!gbPollerThreadShouldExit && !gbPollerRefresh) { BOOLEAN bWaitElapsed = FALSE; dwError = pthread_cond_timedwait( &gSignalPoller, &gSignalPollerMutex, &nextWake); if (dwError == EINTR) { UMN_LOG_DEBUG("User poller cond wait interrupted; continuing."); continue; } if (dwError == ETIMEDOUT) { UMN_LOG_DEBUG("User poller cond wait completed."); dwError = 0; break; } if (dwError != 0) { UMN_LOG_ERROR("Timed wait error: error %s (%d).", ErrnoToName(dwError), dwError); BAIL_ON_UMN_ERROR(dwError); } dwError = UmnSrvTimespecElapsed(&nextWake, &bWaitElapsed); if (dwError == 0 && bWaitElapsed == TRUE) { break; } } gbPollerRefresh = FALSE; if (!gbPollerThreadShouldExit) { dwError = UmnSrvNow(&periodStart, &now); BAIL_ON_UMN_ERROR(dwError); // obtain the fully qualified domain name and use it throughout this iteration UmnEvtFreeEventComputerName(); UmnEvtGetFQDN(fqdn, sizeof(fqdn)); UmnEvtSetEventComputerName(fqdn); dwError = UmnSrvUpdateAccountInfo(now.tv_sec); if (dwError == ERROR_CANCELLED) { UMN_LOG_INFO("User poller cancelled iteration"); dwError = 0; break; } // simply log other errors and attempt to continue if (dwError != LW_ERROR_SUCCESS) { if (LwRegIsRegistrySpecificError(dwError)) { LwRegGetErrorString(dwError, regErrMsg, sizeof(regErrMsg) - 1); UMN_LOG_ERROR("Failed updating account info, registry error = %d %s. Continuing.", dwError, regErrMsg); } else { UMN_LOG_ERROR("Failed updating account info, error = %d symbol = %s %s. Continuing.", dwError, LwWin32ExtErrorToName(dwError), LwWin32ExtErrorToDescription(dwError)); } dwError = 0; } // periodUsed = now - periodStart dwError = UmnSrvNow(&periodUsed, &now); BAIL_ON_UMN_ERROR(dwError); UmnSrvTimespecSubtract( &periodUsed, &periodUsed, &periodStart); UMN_LOG_DEBUG("Account activity update took %f seconds", periodUsed.tv_sec + periodUsed.tv_nsec / (double)NANOSECS_PER_SECOND); } } UMN_LOG_INFO("User poller thread stopped"); cleanup: if (bMutexLocked) { pthread_mutex_unlock(&gSignalPollerMutex); } if (dwError != 0) { UMN_LOG_ERROR( "User monitor polling thread exiting with code %d", dwError); kill(getpid(), SIGTERM); } return NULL; error: goto cleanup; }