Annotation of parser3/src/types/pa_vstatus.C, revision 1.21
1.1 paf 1: /** @file
2: Parser: @b status class impl.
3:
1.17 paf 4: Copyright (c) 2001-2003 ArtLebedev Group (http://www.artlebedev.com)
1.6 paf 5: Author: Alexandr Petrosian <paf@design.ru> (http://paf.design.ru)
1.16 paf 6:
7: Win32 rusage author: Victor Fedoseev <vvf_ru@mail.ru>
1.8 paf 8: */
1.1 paf 9:
1.20 paf 10: static const char * const IDENT_VSTATUS_C="$Date: 2003/11/20 16:34:30 $";
1.1 paf 11:
12: #include "pa_vstatus.h"
13: #include "pa_cache_managers.h"
1.2 paf 14: #include "pa_vhash.h"
15: #include "pa_vdouble.h"
16:
17: #ifdef HAVE_SYS_RESOURCE_H
18: // rusage
19: #include <sys/resource.h>
20: #endif
1.1 paf 21:
1.16 paf 22: #ifdef WIN32
23: #include <windows.h>
24: #include "psapi.h"
25:
26: // should be in windows.h, but were't
27: typedef struct _IO_COUNTERS_ {
28: ULONGLONG ReadOperationCount;
29: ULONGLONG WriteOperationCount;
30: ULONGLONG OtherOperationCount;
31: ULONGLONG ReadTransferCount;
32: ULONGLONG WriteTransferCount;
33: ULONGLONG OtherTransferCount;
34: } IO_COUNTERS_;
35: typedef IO_COUNTERS_ *PIO_COUNTERS_;
36:
37: typedef unsigned __int64 ui64;
38: // kernel32.dll (NT/2K/XP)
39: typedef BOOL (WINAPI *PGETPROCESSTIMES)(HANDLE,LPFILETIME,LPFILETIME,LPFILETIME,LPFILETIME);
40: //typedef BOOL (WINAPI *PGETPROCESSHEAPS)(DWORD,PHANDLE);
41: typedef BOOL (WINAPI *GETPROCESSIOCOUNTERS)(HANDLE,PIO_COUNTERS_);
42: // psapi.dll (2K/XP)
43: typedef BOOL (WINAPI *PGETPROCESSMEMORYINFO)(HANDLE,PPROCESS_MEMORY_COUNTERS,DWORD);
44:
45: // from CRT time.c
46: /*
47: * Number of 100 nanosecond units from 1/1/1601 to 1/1/1970
48: */
49: #define EPOCH_BIAS 116444736000000000i64
50:
51: /*
52: * Union to facilitate converting from FILETIME to unsigned __int64
53: */
54: typedef union {
55: unsigned __int64 ft_scalar;
56: FILETIME ft_struct;
57: } FT;
58:
59: #endif
60:
1.17 paf 61: Value& rusage_element() {
62: VHash& rusage=*new VHash;
63: HashStringValue& hash=rusage.hash();
1.16 paf 64:
65: #ifdef WIN32
1.17 paf 66: double d1;
67: HANDLE hProc = GetCurrentProcess();
1.16 paf 68:
1.17 paf 69: HMODULE hMod = LoadLibrary("kernel32.dll");
70: if(hMod){
71: // NT/2K/XP
72: PGETPROCESSTIMES pGetProcessTimes = (PGETPROCESSTIMES)GetProcAddress(hMod, "GetProcessTimes");
73: if(pGetProcessTimes){
74: FILETIME CreationTime, ExitTime;
75: FT KernelTime, UserTime;
76: if(pGetProcessTimes(hProc, &CreationTime, &ExitTime, &KernelTime.ft_struct, &UserTime.ft_struct)){
77: // dwHighDateTime & dwLowDateTime - 1/10 000 000 seconds in 64 bit
78: /* the amount of time that the process has executed in user mode */
79: d1 = double((LONGLONG)UserTime.ft_scalar)/10000000.0;
1.21 ! paf 80: hash.put(String::Body("utime"), new VDouble(d1));
! 81: // hash.put(String::Body("UserTime"), new VDouble(d1));
1.17 paf 82:
83: /* the amount of time that the process has executed in kernel mode */
84: d1 = double((LONGLONG)KernelTime.ft_scalar)/10000000.0;
1.21 ! paf 85: hash.put(String::Body("stime"), new VDouble(d1));
! 86: // hash.put(String::Body("KernelTime"), new VDouble( d1));
1.16 paf 87: }
1.17 paf 88: }
1.16 paf 89:
1.17 paf 90: // NT/2K/XP
91: GETPROCESSIOCOUNTERS pGetProcessIoCounters = (GETPROCESSIOCOUNTERS)GetProcAddress(hMod, "GetProcessIoCounters");
92: if(pGetProcessIoCounters){
93: IO_COUNTERS_ ioc;
94: if(pGetProcessIoCounters(hProc, &ioc)){
95: /* Specifies the number of I/O operations performed, other than read and write operations */
1.18 paf 96: hash.put(String::Body( "OtherOperationCount"),
1.17 paf 97: new VDouble(double((LONGLONG)ioc.OtherOperationCount)));
98: /* Specifies the number of bytes transferred during operations other than read and write operations */
1.18 paf 99: hash.put(String::Body( "OtherTransferCount"),
1.17 paf 100: new VDouble(double((LONGLONG)ioc.OtherTransferCount)/1024.0));
101: /* Specifies the number of read operations performed */
1.18 paf 102: hash.put(String::Body( "ReadOperationCount"),
1.17 paf 103: new VDouble(double((LONGLONG)ioc.ReadOperationCount)));
104: /* Specifies the number of bytes read */
1.18 paf 105: hash.put(String::Body( "ReadTransferCount"),
1.17 paf 106: new VDouble(double((LONGLONG)ioc.ReadTransferCount)/1024.0));
107: /* Specifies the number of write operations performed */
1.18 paf 108: hash.put(String::Body( "WriteOperationCount"),
1.17 paf 109: new VDouble(double((LONGLONG)ioc.WriteOperationCount)));
110: /* Specifies the number of bytes written */
1.18 paf 111: hash.put(String::Body( "WriteTransferCount"),
1.17 paf 112: new VDouble(double((LONGLONG)ioc.WriteTransferCount)/1024.0));
1.16 paf 113: }
114: }
1.17 paf 115: FreeLibrary(hMod);
116: /*
117: PGETPROCESSHEAPS pGetProcessHeaps = (PGETPROCESSHEAPS)GetProcAddress(hMod, "GetProcessHeaps");
118: if(pGetProcessHeaps){
119: }
120: */
121: }
1.16 paf 122:
1.17 paf 123: // 2K/XP
124: hMod = LoadLibrary("psapi.dll");
125: if(hMod){
126: PGETPROCESSMEMORYINFO pGetProcessMemoryInfo = (PGETPROCESSMEMORYINFO)GetProcAddress(hMod, "GetProcessMemoryInfo");
127: if(pGetProcessMemoryInfo){
128: PROCESS_MEMORY_COUNTERS pmc;
129: pmc.cb = sizeof(PROCESS_MEMORY_COUNTERS);
130: if(pGetProcessMemoryInfo(hProc, &pmc, sizeof(PROCESS_MEMORY_COUNTERS))){
131: /* The peak working set size */
132: d1 = double(pmc.PeakWorkingSetSize)/1024.0;
1.21 ! paf 133: hash.put(String::Body("maxrss"), new VDouble(d1));
! 134: // hash.put(String::Body("PeakWorkingSetSize")), new VDouble( d1)));
1.17 paf 135: /* The peak nonpaged pool usage */
136: d1 = double(pmc.QuotaPeakNonPagedPoolUsage)/1024.0;
1.21 ! paf 137: // hash.put(String::Body("ixrss"), new VDouble(d1));
! 138: hash.put(String::Body("QuotaPeakNonPagedPoolUsage"), new VDouble( d1));
1.17 paf 139: /* The peak paged pool usage */
140: d1 = double(pmc.QuotaPeakPagedPoolUsage)/1024.0;
1.21 ! paf 141: // hash.put(String::Body("idrss"), new VDouble( d1));
! 142: hash.put(String::Body("QuotaPeakPagedPoolUsage"), new VDouble( d1));
1.17 paf 143: /* The peak pagefile usage */
144: d1 = double(pmc.PeakPagefileUsage)/1024.0;
1.21 ! paf 145: // hash.put(String::Body("isrss"), new VDouble( d1));
! 146: hash.put(String::Body("PeakPagefileUsage"), new VDouble( d1));
1.16 paf 147: }
148: }
1.17 paf 149: FreeLibrary(hMod);
150: }
1.16 paf 151:
1.17 paf 152: // all windows.
153: FT ft;
154: GetSystemTimeAsFileTime( &(ft.ft_struct) );
155: ft.ft_scalar -= EPOCH_BIAS;
156: ui64 tv_sec = ft.ft_scalar/10000000i64;
157: ui64 tv_usec = (ft.ft_scalar-tv_sec*10000000i64)/10i64;
1.21 ! paf 158: hash.put(String::Body("tv_sec"), new VDouble(double((LONGLONG)tv_sec)));
! 159: hash.put(String::Body("tv_usec"), new VDouble(double((LONGLONG)tv_usec)));
1.16 paf 160:
161: #else
162:
163: #ifdef HAVE_GETRUSAGE
1.17 paf 164: struct rusage u;
165: if(getrusage(RUSAGE_SELF,&u)<0)
166: throw Exception(0,
167: 0,
168: "getrusage failed (#%d)", errno);
169:
1.21 ! paf 170: hash.put(String::Body("utime"), new VDouble(
1.17 paf 171: u.ru_utime.tv_sec+u.ru_utime.tv_usec/1000000.0));
1.21 ! paf 172: hash.put(String::Body("stime"), new VDouble(
1.17 paf 173: u.ru_stime.tv_sec+u.ru_stime.tv_usec/1000000.0));
1.21 ! paf 174: hash.put(String::Body("maxrss"), new VDouble(u.ru_maxrss));
! 175: hash.put(String::Body("ixrss"), new VDouble(u.ru_ixrss));
! 176: hash.put(String::Body("idrss"), new VDouble(u.ru_idrss));
! 177: hash.put(String::Body("isrss"), new VDouble(u.ru_isrss));
1.16 paf 178: #endif
1.13 paf 179:
180: #ifdef HAVE_GETTIMEOFDAY
1.17 paf 181: struct timeval tp;
182: if(gettimeofday(&tp, NULL)<0)
183: throw Exception(0,
184: 0,
185: "gettimeofday failed (#%d)", errno);
186:
1.21 ! paf 187: hash.put(String::Body("tv_sec"), new VDouble(tp.tv_sec));
! 188: hash.put(String::Body("tv_usec"), new VDouble(tp.tv_usec));
1.17 paf 189: #endif
1.16 paf 190:
1.13 paf 191: #endif
1.1 paf 192:
1.17 paf 193: return rusage;
194: }
195:
196: #ifndef PA_DEBUG_DISABLE_GC
197: Value& memory_element() {
198: VHash& memory=*new VHash;
199: HashStringValue& hash=memory.hash();
200: size_t heap_size=GC_get_heap_size();
201: size_t free_bytes=GC_get_free_bytes();
202: size_t bytes_since_gc=GC_get_bytes_since_gc();
203: size_t total_bytes=GC_get_total_bytes();
204:
1.21 ! paf 205: hash.put(String::Body("used"), new VDouble((heap_size-free_bytes)/1024.0));
! 206: hash.put(String::Body("free"), new VDouble(free_bytes/1024.0));
! 207: hash.put(String::Body("ever_allocated_since_compact"), new VDouble(bytes_since_gc/1024.0));
! 208: hash.put(String::Body("ever_allocated_since_start"), new VDouble(total_bytes/1024.0));
1.17 paf 209:
210: return memory;
211: }
1.16 paf 212: #endif
213:
1.17 paf 214: Value* VStatus::get_element(const String& aname, Value& /*aself*/, bool /*looking_up*/) {
215: // getstatus
216: if(Cache_manager* manager=cache_managers.get(aname))
217: return manager->get_status();
218:
219: // rusage
220: if(aname=="rusage")
221: return &rusage_element();
222:
223: #ifndef PA_DEBUG_DISABLE_GC
224: // memory
225: if(aname=="memory")
226: return &memory_element();
227: #endif
1.1 paf 228:
229: return 0;
230: }
E-mail: