Annotation of parser3/src/types/pa_vstatus.C, revision 1.36

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

E-mail: