230 lines
6.1 KiB
C
230 lines
6.1 KiB
C
|
/*++
|
|||
|
|
|||
|
Copyright (c) 1992-1997 Microsoft Corporation
|
|||
|
|
|||
|
Module Name:
|
|||
|
|
|||
|
uptime.c
|
|||
|
|
|||
|
Abstract:
|
|||
|
|
|||
|
Contains routines to calculate sysUpTime.
|
|||
|
|
|||
|
SnmpSvcInitUptime
|
|||
|
SnmpSvcGetUptime
|
|||
|
SnmpSvcGetUptimeFromTime
|
|||
|
|
|||
|
Environment:
|
|||
|
|
|||
|
User Mode - Win32
|
|||
|
|
|||
|
Revision History:
|
|||
|
|
|||
|
--*/
|
|||
|
|
|||
|
///////////////////////////////////////////////////////////////////////////////
|
|||
|
// //
|
|||
|
// Include files //
|
|||
|
// //
|
|||
|
///////////////////////////////////////////////////////////////////////////////
|
|||
|
|
|||
|
#include <nt.h>
|
|||
|
#include <windef.h>
|
|||
|
#include <ntrtl.h>
|
|||
|
#include <nturtl.h>
|
|||
|
#include <windows.h>
|
|||
|
#include <snmp.h>
|
|||
|
#include <snmputil.h>
|
|||
|
#include <ntfuncs.h>
|
|||
|
|
|||
|
|
|||
|
///////////////////////////////////////////////////////////////////////////////
|
|||
|
// //
|
|||
|
// Global Variables //
|
|||
|
// //
|
|||
|
///////////////////////////////////////////////////////////////////////////////
|
|||
|
|
|||
|
DWORD g_dwUpTimeReference = 0;
|
|||
|
LONGLONG g_llUpTimeReference = 0;
|
|||
|
|
|||
|
|
|||
|
|
|||
|
///////////////////////////////////////////////////////////////////////////////
|
|||
|
// //
|
|||
|
// Private Definitions //
|
|||
|
// //
|
|||
|
///////////////////////////////////////////////////////////////////////////////
|
|||
|
|
|||
|
#define INVALID_UPTIME 0xFFFFFFFF
|
|||
|
|
|||
|
|
|||
|
///////////////////////////////////////////////////////////////////////////////
|
|||
|
// //
|
|||
|
// Private Procedures //
|
|||
|
// //
|
|||
|
///////////////////////////////////////////////////////////////////////////////
|
|||
|
|
|||
|
DWORD
|
|||
|
SNMP_FUNC_TYPE
|
|||
|
SnmpSvcInitUptime(
|
|||
|
)
|
|||
|
|
|||
|
/*++
|
|||
|
|
|||
|
Routine Description:
|
|||
|
|
|||
|
Initializes sysUpTime reference for SNMP process.
|
|||
|
|
|||
|
Arguments:
|
|||
|
|
|||
|
None.
|
|||
|
|
|||
|
Return Values:
|
|||
|
|
|||
|
Returns sysUpTime reference to pass to subagents.
|
|||
|
|
|||
|
--*/
|
|||
|
|
|||
|
{
|
|||
|
NTSTATUS NtStatus;
|
|||
|
SYSTEM_TIMEOFDAY_INFORMATION TimeOfDay;
|
|||
|
|
|||
|
// obtain reference the outdated way
|
|||
|
g_dwUpTimeReference = GetCurrentTime();
|
|||
|
|
|||
|
|
|||
|
// query time in spiffy new precise manner
|
|||
|
NtStatus = NtQuerySystemInformation(
|
|||
|
SystemTimeOfDayInformation,
|
|||
|
&TimeOfDay,
|
|||
|
sizeof(SYSTEM_TIMEOFDAY_INFORMATION),
|
|||
|
NULL
|
|||
|
);
|
|||
|
|
|||
|
// validate return code
|
|||
|
if (NT_SUCCESS(NtStatus)) {
|
|||
|
|
|||
|
// initialize higher precision startup time
|
|||
|
g_llUpTimeReference = TimeOfDay.CurrentTime.QuadPart;
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
//
|
|||
|
// The algorithm for subagents to calculate sysUpTime
|
|||
|
// is based on GetCurrentTime() which returns the time
|
|||
|
// in milliseconds and therefore wraps every 49.71 days.
|
|||
|
// RFC1213 specifies that sysUpTime is to be returned in
|
|||
|
// centaseconds but we cannot break existing subagents.
|
|||
|
// The old value is returned to the master agent here
|
|||
|
// but newer subagents should use SnmpUtilGetUpTime.
|
|||
|
//
|
|||
|
|
|||
|
return g_dwUpTimeReference;
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
///////////////////////////////////////////////////////////////////////////////
|
|||
|
// //
|
|||
|
// Public Procedures //
|
|||
|
// //
|
|||
|
///////////////////////////////////////////////////////////////////////////////
|
|||
|
|
|||
|
DWORD
|
|||
|
SNMP_FUNC_TYPE
|
|||
|
SnmpSvcGetUptime(
|
|||
|
)
|
|||
|
|
|||
|
/*++
|
|||
|
|
|||
|
Routine Description:
|
|||
|
|
|||
|
Retrieves sysUpTime for SNMP process.
|
|||
|
|
|||
|
Arguments:
|
|||
|
|
|||
|
None.
|
|||
|
|
|||
|
Return Values:
|
|||
|
|
|||
|
Returns sysUpTime value for use by subagents.
|
|||
|
|
|||
|
--*/
|
|||
|
|
|||
|
{
|
|||
|
DWORD dwUpTime = INVALID_UPTIME;
|
|||
|
|
|||
|
NTSTATUS NtStatus;
|
|||
|
SYSTEM_TIMEOFDAY_INFORMATION TimeOfDay;
|
|||
|
|
|||
|
// query time in spiffy new precise manner
|
|||
|
NtStatus = NtQuerySystemInformation(
|
|||
|
SystemTimeOfDayInformation,
|
|||
|
&TimeOfDay,
|
|||
|
sizeof(SYSTEM_TIMEOFDAY_INFORMATION),
|
|||
|
NULL
|
|||
|
);
|
|||
|
|
|||
|
// validate return code
|
|||
|
if (NT_SUCCESS(NtStatus)) {
|
|||
|
LARGE_INTEGER liUpTime;
|
|||
|
LARGE_INTEGER liUpTimeInCentaseconds;
|
|||
|
|
|||
|
// calculate difference from reference
|
|||
|
liUpTime.QuadPart = TimeOfDay.CurrentTime.QuadPart -
|
|||
|
g_llUpTimeReference;
|
|||
|
|
|||
|
// convert 100ns units (10^-7) into centasecond units (10^-2)
|
|||
|
liUpTimeInCentaseconds = RtlExtendedLargeIntegerDivide(
|
|||
|
liUpTime,
|
|||
|
100000,
|
|||
|
NULL
|
|||
|
);
|
|||
|
|
|||
|
// convert large integer to dword value
|
|||
|
dwUpTime = (DWORD)(LONGLONG)liUpTimeInCentaseconds.QuadPart;
|
|||
|
|
|||
|
} else if (g_dwUpTimeReference != 0) {
|
|||
|
|
|||
|
// calculate difference from reference
|
|||
|
dwUpTime = (GetCurrentTime() - g_dwUpTimeReference) / 10;
|
|||
|
}
|
|||
|
|
|||
|
return dwUpTime;
|
|||
|
}
|
|||
|
|
|||
|
DWORD
|
|||
|
SNMP_FUNC_TYPE
|
|||
|
SnmpSvcGetUptimeFromTime(
|
|||
|
DWORD dwUpTime
|
|||
|
)
|
|||
|
|
|||
|
/*++
|
|||
|
|
|||
|
Routine Description:
|
|||
|
|
|||
|
Retrieves sysUpTime value for a given tick count.
|
|||
|
|
|||
|
Arguments:
|
|||
|
|
|||
|
dwUpTime - stack uptime (in centaseconds) to convert to sysUpTime
|
|||
|
|
|||
|
Return Values:
|
|||
|
|
|||
|
Returns sysUpTime value for use by subagents.
|
|||
|
|
|||
|
--*/
|
|||
|
|
|||
|
{
|
|||
|
DWORD dwUpTimeReferenceInCentaseconds;
|
|||
|
|
|||
|
// convert 100ns units (10^-7) into centasecond units (10^-2)
|
|||
|
dwUpTimeReferenceInCentaseconds = (DWORD)(g_llUpTimeReference / 100000);
|
|||
|
|
|||
|
if (dwUpTime < dwUpTimeReferenceInCentaseconds) {
|
|||
|
return 0;
|
|||
|
}
|
|||
|
|
|||
|
// calculate difference from reference
|
|||
|
return dwUpTime - dwUpTimeReferenceInCentaseconds;
|
|||
|
}
|