Added code to change sampling rate as bucket width changes (this is not
[dyninst.git] / paradyn / src / DMthread / DMmetric.h
1 /*
2  * Copyright (c) 1993, 1994 Barton P. Miller, Jeff Hollingsworth,
3  *     Bruce Irvin, Jon Cargille, Krishna Kunchithapadam, Karen
4  *     Karavanic, Tia Newhall, Mark Callaghan.  All rights reserved.
5  *
6  * This software is furnished under the condition that it may not be
7  * provided or otherwise made available to, or used by, any other
8  * person, except as provided for by the terms of applicable license
9  * agreements.  No title to or ownership of the software is hereby
10  * transferred.  The name of the principals may not be used in any
11  * advertising or publicity related to this software without specific,
12  * written prior authorization.  Any use of this software must include
13  * the above copyright notice.
14  *
15  */
16 #ifndef dmmetric_H
17 #define dmmetric_H
18 #include "util/h/sys.h"
19 #include "util/h/hist.h"
20 #include "dataManager.thread.h"
21 #include "dataManager.thread.SRVR.h"
22 #include <string.h>
23 #include "paradyn/src/UIthread/Status.h"
24 #include <stdlib.h>
25 #include "util/h/Vector.h"
26 #include "util/h/Dictionary.h"
27 #include "util/h/String.h"
28 #include "util/h/aggregateSample.h"
29 #include "DMinclude.h"
30 #include "DMdaemon.h"
31
32
33 class metricInstance;
34
35 // a part of an mi.
36 //
37 class component {
38     friend class metricInstance;
39     friend class paradynDaemon;
40     public:
41         component(paradynDaemon *d, int i, metricInstance *mi) {
42             daemon = d;
43             id = i;
44             // Is this add unique?
45             assert(i >= 0);
46             d->activeMids[(unsigned)id] = mi;
47         }
48         ~component() {
49             daemon->disableDataCollection(id);
50             assert(id>=0);
51             daemon->disabledMids += (unsigned) id;
52             daemon->activeMids.undef((unsigned)id);
53         }
54         int getId(){return(id);}
55         paradynDaemon *getDaemon() { return(daemon); }
56
57     private:
58         sampleInfo sample;
59         paradynDaemon *daemon;
60         int id;
61 };
62
63
64 //
65 //  info about a metric in the system
66 //
67 class metric {
68     friend class dataManager;
69     friend class metricInstance;
70     friend class paradynDaemon;
71     friend void addMetric(T_dyninstRPC::metricInfo &info);
72     friend metricInstance *DMenableData(perfStreamHandle, metricHandle,
73                                         resourceListHandle, phaseType,
74                                         unsigned, unsigned);
75
76     friend void histDataCallBack(sampleValue *, timeStamp , 
77                                  int , int , void *);
78     // TODO: remove these when PC is re-written ***************
79     friend void PCmetricFunc(perfStreamHandle, const char *name,
80                              int style, int aggregate,
81                              const char *units, metricHandle m_handle);
82     friend void PCmain(void* varg);
83     friend class PCmetric;
84     friend void PCnewData(perfStreamHandle,metricInstanceHandle,
85                           int,sampleValue,phaseType);
86     // ********************************************************
87     public:
88         metric(T_dyninstRPC::metricInfo i); 
89         const T_dyninstRPC::metricInfo  *getInfo() { return(&info); }
90         const char *getName() { return((info.name.string_of()));}
91         const char *getUnits() { return((info.units.string_of()));}
92         metricHandle getHandle() { return(info.handle);}
93         metricStyle  getStyle() { return((metricStyle) info.style); }
94         int   getAggregate() { return info.aggregate;}
95
96         static unsigned  size(){return(metrics.size());}
97         static const T_dyninstRPC::metricInfo  *getInfo(metricHandle handle);
98         static const char *getName(metricHandle handle);
99         static const metricHandle  *find(const string name); 
100         static vector<string> *allMetricNames();
101         static vector<met_name_id> *allMetricNamesIds();
102
103     private:
104         static dictionary_hash<string, metric*> allMetrics;
105         static vector<metric*> metrics;  // indexed by metric id
106         T_dyninstRPC::metricInfo info;
107
108         static metric  *getMetric(metricHandle iName); 
109 };
110
111 struct archive_type {
112     Histogram *data;
113     phaseHandle phaseId;
114 };
115
116 typedef struct archive_type ArchiveType;
117
118 class metricInstance {
119     friend class dataManager;
120     friend class metric;
121     friend class paradynDaemon;
122     friend void histDataCallBack(sampleValue *buckets, timeStamp, int count, 
123                                  int first, void *arg);
124     friend metricInstance *DMenableData(perfStreamHandle,metricHandle,
125                                         resourceListHandle,phaseType,
126                                         unsigned, unsigned);
127     // TODO: remove these when PC is re-written ***************
128     friend void PCnewData(perfStreamHandle,metricInstanceHandle,
129                           int,sampleValue,phaseType);
130     friend class datum;
131     friend class PCmetric;
132     // ********************************************************
133     public:
134         metricInstance(resourceListHandle rl, metricHandle m,phaseHandle ph);
135         ~metricInstance(); 
136         float getValue() {
137             float ret;
138             if (!data) abort();
139             ret = data->getValue();
140             ret /= enabledTime;
141             return(ret);
142         }
143         float getTotValue() {
144             float ret;
145
146             if (!data) abort();
147             ret = data->getValue();
148             return(ret);
149         }
150         int currUsersCount(){return(users.size());}
151         int globalUsersCount(){return(global_users.size());}
152         int getSampleValues(sampleValue*, int, int, phaseType);
153         int getArchiveValues(sampleValue*, int, int, phaseHandle);
154
155         static unsigned  mhash(const metricInstanceHandle &val){
156             return((unsigned)val);
157         }
158         metricInstanceHandle getHandle(){ return(id); }
159         metricHandle getMetricHandle(){ return(met); }
160         resourceListHandle getFocusHandle(){ return(focus); }
161         void addInterval(timeStamp s,timeStamp e,sampleValue v,bool b){
162              if(data) 
163                  data->addInterval(s,e,v,b);
164              if(global_data)
165                  global_data->addInterval(s,e,v,b);
166         }
167         // void disableDataCollection(perfStreamHandle ps);
168
169         bool isCurrHistogram(){if (data) return(true); else return(false);}
170         bool isEnabled(){return(enabled);}
171         void setEnabled(){ enabled = true;}
172         void clearEnabled(){ enabled = false;}
173         void setPersistentData(){ persistent_data = true; } 
174         void setPersistentCollection(){ persistent_collection = true; } 
175         void clearPersistentData(){ persistent_data = false; } 
176         void clearPersistentCollection(){ persistent_collection = false; } 
177         bool isDataPersistent(){ return persistent_data;}
178         bool isCollectionPersistent(){ return persistent_collection;}
179         // returns false if componet was already on list (not added)
180         bool addComponent(component *new_comp);
181         bool addPart(sampleInfo *new_part);
182
183         static timeStamp GetGlobalWidth(){return(global_bucket_width);}
184         static timeStamp GetCurrWidth(){return(curr_bucket_width);}
185         static void SetGlobalWidth(timeStamp nw){global_bucket_width = nw;}
186         static void SetCurrWidth(timeStamp nw){curr_bucket_width = nw;}
187         static phaseHandle GetCurrPhaseId(){return(curr_phase_id);}
188         static void setPhaseId(phaseHandle ph){curr_phase_id = ph;}
189         static void stopAllCurrentDataCollection(phaseHandle);
190         static u_int numGlobalHists(){ return(num_global_hists); }
191         static u_int numCurrHists(){ return(num_curr_hists); }
192         static void incrNumGlobalHists(){ num_global_hists++; }
193         static void incrNumCurrHists(){ num_curr_hists++; }
194         static void decrNumCurrHists(){ if(num_curr_hists) num_curr_hists--; }
195         static void decrNumGlobalHists(){ if(num_global_hists) num_global_hists--; }
196
197     private:
198         metricHandle met;
199         resourceListHandle focus;
200         float enabledTime;
201         bool enabled;    // set if data for mi is currently enabled
202         vector<sampleInfo *> parts;
203         vector<component *> components;
204
205         vector<perfStreamHandle> users;  // subscribers to curr. phase data
206         Histogram *data;                 // data corr. to curr. phase
207         vector<perfStreamHandle> global_users;  // subscribers to global data
208         Histogram *global_data;     // data corr. to global phase
209         vector<ArchiveType *> old_data;  // histograms of data from old phases 
210         
211         // if set, archive old data on disable and on new phase definition
212         bool persistent_data;  
213         // if set, don't disable on new phase definition
214         bool persistent_collection; 
215
216         unsigned id;
217         sampleInfo sample;
218         static dictionary_hash<metricInstanceHandle,metricInstance *> 
219             allMetricInstances;
220
221         // vector of ids...reuse ids of deleted metricInstances
222         static vector<bool> nextId;
223
224         // info. about phase data
225         static phaseHandle curr_phase_id;  // TODO: set this on Startphase
226         static timeStamp global_bucket_width;  // updated on fold
227         static timeStamp curr_bucket_width;    // updated on fold
228         static u_int num_curr_hists; // num of curr. phase active histograms 
229         static u_int num_global_hists; // num of global phase active histograms 
230
231         static metricInstance *getMI(metricInstanceHandle);
232         static metricInstance *find(metricHandle, resourceListHandle);
233         void newCurrDataCollection(metricStyle,dataCallBack,foldCallBack);
234         void newGlobalDataCollection(metricStyle,dataCallBack,foldCallBack);
235         void addCurrentUser(perfStreamHandle p); 
236         void addGlobalUser(perfStreamHandle p); 
237         // clear enabled flag and remove comps and parts
238         void dataDisable();  
239         void removeGlobalUser(perfStreamHandle);
240         void removeCurrUser(perfStreamHandle);
241         bool deleteCurrHistogram();
242 };
243 #endif