changed parameters to DM_sequential_init
[dyninst.git] / paradyn / src / DMthread / DMresource.C
1 /*
2  *  Copyright 1993 Jeff Hollingsworth.  All rights reserved.
3  *
4  */
5
6 /*
7  * resource.C - handle resource creation and queries.
8  * 
9  * $Log: DMresource.C,v $
10  * Revision 1.27  1995/08/20 03:37:15  newhall
11  * changed parameters to DM_sequential_init
12  * added persistent data and persistent collection flags
13  *
14  * Revision 1.26  1995/08/08  03:10:08  newhall
15  * bug fix to DMresourceListNameCompare
16  * changed newPerfData and sampleDataCallbackFunc definitions
17  *
18  * Revision 1.25  1995/08/01  02:11:20  newhall
19  * complete implementation of phase interface:
20  *   - additions and changes to DM interface functions
21  *   - changes to DM classes to support data collection at current or
22  *     global phase granularity
23  * added alphabetical ordering to foci name creation
24  *
25  * Revision 1.23  1995/07/15 03:34:53  karavan
26  * fixed "paradyn suppress searchChildren" command by checking for parent's
27  * suppress value in resource constructor.
28  *
29  * Revision 1.22  1995/06/02  20:48:28  newhall
30  * * removed all pointers to datamanager class objects from datamanager
31  *    interface functions and from client threads, objects are now
32  *    refered to by handles or by passing copies of DM internal data
33  * * removed applicationContext class from datamanager
34  * * replaced List and HTable container classes with STL containers
35  * * removed global variables from datamanager
36  * * remove redundant lists of class objects from datamanager
37  * * some reorginization and clean-up of data manager classes
38  * * removed all stringPools and stringHandles
39  * * KLUDGE: there are PC friend members of DM classes that should be
40  *    removed when the PC is re-written
41  *
42  * Revision 1.20  1995/03/02  04:23:21  krisna
43  * warning and bug fixes.
44  *
45  * Revision 1.19  1995/02/16  08:17:30  markc
46  * Changed Boolean to bool
47  * Added function to convert char* lists to vector<string>
48  *
49  * Revision 1.18  1995/01/26  17:58:24  jcargill
50  * Changed igen-generated include files to new naming convention; fixed
51  * some bugs compiling with gcc-2.6.3.
52  *
53  * Revision 1.17  1994/11/07  08:24:40  jcargill
54  * Added ability to suppress search on children of a resource, rather than
55  * the resource itself.
56  *
57  * Revision 1.16  1994/11/04  08:46:00  jcargill
58  * Made suppressSearch flag be inherited from parent resource.  Solves the
59  * problem of having to wait for processes to be defined to suppress them.
60  *
61  * Revision 1.15  1994/09/30  21:17:44  newhall
62  * changed convertToStringList method function return value from
63  * stringHandle * to char**
64  *
65  * Revision 1.14  1994/09/30  19:17:51  rbi
66  * Abstraction interface change.
67  *
68  * Revision 1.13  1994/09/22  00:57:16  markc
69  * Entered stringHandles into stringPool rather than assigning from const char *
70  * Added casts to remove compiler warnings
71  *
72  * Revision 1.12  1994/08/05  16:04:00  hollings
73  * more consistant use of stringHandle vs. char *.
74  *
75  * Revision 1.11  1994/07/28  22:31:09  krisna
76  * include <rpc/types.h>
77  * stringCompare to match qsort prototype
78  * proper prorotypes for starting DMmain
79  *
80  * Revision 1.10  1994/07/26  20:03:06  hollings
81  * added suppressSearch.
82  *
83  * Revision 1.9  1994/07/14  23:45:31  hollings
84  * Changed printf of resource to be TCL list like.
85  *
86  * Revision 1.8  1994/06/27  21:23:31  rbi
87  * Abstraction-specific resources and mapping info
88  *
89  * Revision 1.7  1994/06/17  00:11:55  hollings
90  * Fixed off by one error in string canonical string name code.
91  *
92  * Revision 1.6  1994/06/14  15:25:03  markc
93  * Added new call (sameRoot) to the resource class.  This call is used to
94  * determine if two resources have the same parent but are not in an
95  * ancestor-descendant relationship.  Such a relationship implies a conflict
96  * in the two foci.
97  *
98  * Revision 1.5  1994/06/02  16:08:17  hollings
99  * fixed duplicate naming problem for printResources.
100  *
101  * Revision 1.4  1994/05/31  19:11:34  hollings
102  * Changes to permit direct access to resources and resourceLists.
103  *
104  * Revision 1.3  1994/04/18  22:28:33  hollings
105  * Changes to create a canonical form of a resource list.
106  *
107  * Revision 1.2  1994/02/03  23:26:59  hollings
108  * Changes to work with g++ version 2.5.2.
109  *
110  * Revision 1.1  1994/02/02  00:42:35  hollings
111  * Changes to the Data manager to reflect the file naming convention and
112  * to support the integration of the Performance Consultant.
113  *
114  *
115  */
116 #include <stdio.h>
117 #include <stdlib.h>
118 #include <string.h>
119
120 #include "dataManager.thread.h"
121 #include "DMresource.h"
122
123 /*  TODO: remove this
124 char *resource::createname(vector<string>& res_name){
125
126   char *tempName = new char[255];
127   unsigned j = 0;
128   unsigned i = 0;
129   for(; i < res_name.size()-1;i++){
130       sprintf(&(tempName[j]), "%s/", res_name[i].string_of());
131       j += res_name[i].length()+1;
132   }
133   if(i>0){
134      sprintf(&(tempName[j]),"%s",res_name[i].string_of());
135   }
136   return(tempName);
137   tempName = 0;
138 }
139 */
140
141 //
142 // used only to construct root.
143 //
144 resource::resource()
145 {
146     string temp = ""; 
147     if(!allResources.defines(temp)){
148         name = temp; 
149         res_handle = resources.size();
150         parent = res_handle; 
151         suppressSearch = FALSE;
152         suppressChildSearch = FALSE;
153         abstr = NULL;
154         resource *res = this;
155         resources += res;
156         allResources[name] = res;
157     }
158 }
159
160 resource::resource(resourceHandle p_handle, 
161                    vector<string>& resource_name,
162                    string& r_name,
163                    string& a) 
164 {
165     
166     if(!allResources.defines(r_name)){
167         name = r_name;
168         res_handle = resources.size();
169         parent = p_handle;
170         fullName = resource_name;
171         resource *p = resources[parent];
172          
173         suppressSearch = p->getSuppressChildren();
174         suppressChildSearch = suppressSearch; // check for suppress
175                                               // of parent's children
176         abstr = AMfind(a.string_of());
177         resource *res = this;
178         allResources[name] = res;
179         resources += res;
180         p->AddChild(res_handle);
181     }
182 }
183
184 resource *resource::handle_to_resource(resourceHandle r_handle) {
185      if (r_handle < resources.size()) {
186          return(resources[r_handle]);    
187      }
188      return(NULL);
189 }
190 vector<resourceHandle> *resource::getChildren(){
191
192     vector<resourceHandle> *temp = new vector<resourceHandle>;
193     for(unsigned i=0; i < children.size(); i++){
194         *temp += (resources[children[i]])->getHandle();      
195     }
196     return(temp);
197 }
198
199 resourceHandle *resource::findChild(const char *nm){
200     string temp = nm;
201     for(unsigned i=0; i < children.size(); i++){
202         if((resources[children[i]])->match(temp)){
203              resourceHandle *h = new resourceHandle;
204              *h = children[i];
205              return(h);
206              h = 0;
207         }
208     }
209     return(0);  // not found
210 }
211
212
213 void resource::print()
214 {
215     printf("%s ", name.string_of());
216 }
217
218 bool resource::string_to_handle(string res,resourceHandle *h){
219     if(allResources.defines(res)){
220        resource *temp = allResources[res];
221        *h = temp->getHandle();
222        return(TRUE);
223     }
224     else
225     return(FALSE);
226 }
227
228 /*
229  * Convinence function.
230  *
231  */
232 #ifdef ndef
233 bool resource::isDescendent(resourceHandle child)
234 {
235     for(unsigned i=0; i < children.size(); i++){
236         if(child == children[i])
237             return(TRUE);
238     }
239     return(FALSE);
240 }
241 #endif
242
243 bool resource::isDescendent(resourceHandle child_handle)
244 {
245     resourceHandle root_handle = rootResource->getHandle();
246     resourceHandle this_handle = getHandle();
247     if (this_handle == child_handle) 
248         return FALSE;
249     if (this_handle == root_handle) 
250             return TRUE;
251     while (child_handle != root_handle) {
252         if (child_handle == this_handle) {
253             return TRUE;
254         } else {
255             child_handle = handle_to_resource(child_handle)->getParent();
256         }
257     }
258     return FALSE;
259 }
260
261
262
263 /*
264  * Do the two resources have the same base?
265  * Note, since the there is a common root for all nodes,
266  * the test for a common base checks the node below the
267  * common root.
268  */
269 bool resource::sameRoot(resourceHandle other)
270 {
271   resource *myBase=0, *otherBase=0, *temp;
272
273   temp = this;
274   resourceHandle root = rootResource->getHandle(); 
275   while (temp->getHandle() != root) {
276     myBase = temp;
277     temp = handle_to_resource(temp->parent);
278   }
279   temp = handle_to_resource(other);
280   while (temp->getHandle() != root) {
281     otherBase = temp;
282     temp = handle_to_resource(temp->parent);
283   }
284   if (myBase == otherBase)
285     return TRUE;
286   else
287     return FALSE;
288 }
289
290 const char *resource::getName(resourceHandle h){
291
292     if(h < resources.size()){
293         resource *res = resources[h];
294         return(res->getName());
295     }
296     return 0;
297 }
298
299 resource *resource::string_to_resource(string res){
300
301     if(allResources.defines(res)){
302         return(allResources[res]);
303     }
304     return 0;
305 }
306
307 int DMresourceListNameCompare(const void *n1, const void *n2){
308     
309     const string *s1 = (const string*)n1, *s2 = (const string*)n2;
310     if(*s1 > *s2)
311        return(1);
312     if(*s1 == *s2)
313        return(0);
314     else
315        return(-1);
316
317 }
318
319 string DMcreateRLname(const vector<resourceHandle> &res){
320     // create a unique name
321     string temp;
322     resource *next;
323
324     vector <string> sorted_names;
325
326     unsigned i=0;
327     for(; i < res.size(); i++){
328         next = resource::handle_to_resource(res[i]);
329         sorted_names += next->getFullName();
330     }
331     sorted_names.sort(DMresourceListNameCompare);
332
333     for(i=0; i < (res.size() - 1); i++){
334         temp += sorted_names[i].string_of();
335         temp += ",";
336     }
337     if(res.size() > 0){
338         temp += sorted_names[i].string_of();
339     }
340     return(temp);
341 }
342
343 resourceList::resourceList(const vector<resourceHandle> &res){
344     // create a unique name
345     string temp = DMcreateRLname(res);
346     // see if this resourceList has been created already, if not add it
347     if(!allFoci.defines(temp)){
348         id = foci.size();
349         resourceList *rl = this;
350         allFoci[temp] = rl;
351         fullName = temp;
352         foci += rl;
353
354         // create elements vector 
355         for(unsigned i=0; i < res.size(); i++){
356             elements += resource::handle_to_resource(res[i]);
357             // elements += r;
358     } }
359     else {
360         printf("ERROR: this resourceList already created: %s\n",temp.string_of());
361     }
362 }
363
364 // this should be called with strings of fullNames for resources
365 // ex.  "/Procedure/blah.c/foo"  rather than "foo"
366 resourceList::resourceList(const vector<string> &names){
367     // create a unique name
368     unsigned size = names.size();
369     string temp;
370     unsigned i=0;
371     for(; i < size; i++){
372        temp += names[i]; 
373        if(i < (size-1)){
374            temp += ",";
375        }
376     }
377     // see if this resourceList has been created already, if not add it
378     if(!allFoci.defines(temp)){
379         id = foci.size();
380         resourceList *rl = this;
381         allFoci[temp] = rl;
382         fullName = temp;
383         foci += rl;
384         // create elements vector 
385         for(i=0; i < size; i++){
386             elements += resource::string_to_resource(names[i]);
387     } }
388     else {
389         printf("ERROR: this resourceList already created: %s\n",temp.string_of());
390     }
391 }
392
393
394 void resourceList::print()
395 {
396     printf("{");
397     for (unsigned i=0; i < elements.size(); i++) {
398         if (i) printf(" ");
399         printf("{");
400         elements[i]->print();
401         printf("}");
402     }
403     printf("}");
404 }
405
406 #ifdef n_def
407 bool resourceList::convertToStringList(vector<string> &vs) {
408     for (unsigned i=0; i < elements.size(); i++)
409       vs += elements[i]->getFullName();
410     return true;
411 }
412 #endif
413
414 bool resourceList::convertToStringList(vector< vector<string> > &fs) {
415     for (unsigned i=0; i < elements.size(); i++)
416         fs += elements[i]->getParts();
417     return true;
418 }
419
420 bool resourceList::convertToIDList(vector<u_int> &fs) {
421     for (unsigned i=0; i < elements.size(); i++){
422         fs += elements[i]->getHandle();
423     }
424     return true;
425 }
426
427
428 const char *resourceList::getName(resourceListHandle rh){
429
430     if(rh < foci.size()){
431         resourceList *rl = foci[rh];
432         return(rl->getName());
433     }
434     return(NULL);
435 }
436
437 vector<resourceHandle> *resourceList::getResourceHandles(resourceListHandle h){
438
439     resourceList *focus = getFocus(h);
440     if(focus){
441         vector<resourceHandle> *handles = new vector<resourceHandle>;
442         for(unsigned i=0; i < focus->elements.size(); i++){
443             resource *part = focus->elements[i];
444             *handles += part->getHandle(); 
445         }
446         return(handles);
447     }
448     return(NULL);
449
450 }
451
452 const resourceListHandle *resourceList::find(const string &name){
453
454     if(allFoci.defines(name)){
455         resourceList *res_list = allFoci[name]; 
456         const resourceListHandle *h = &res_list->id;
457         return(h);
458         res_list = 0;
459     }
460     return 0;
461
462
463 }
464
465 resourceListHandle resourceList::getResourceList(
466                                 const vector<resourceHandle>& h){
467
468     // does this resourceList already exist?
469     string temp = DMcreateRLname(h);
470     if(allFoci.defines(temp)){
471         resourceList *rl = allFoci[temp];
472         return(rl->getHandle());
473     }
474     // create a new resourceList
475     resourceList *res = new resourceList(h);
476     assert(res);
477     return(res->getHandle());
478 }
479
480 resourceList *resourceList::getFocus(resourceListHandle handle){
481
482     if(handle < foci.size())
483         return(foci[handle]);
484     return 0;
485 }
486
487 resourceList *resourceList::findRL(const char *name){
488     string temp = name;
489     if(allFoci.defines(name)){
490         return allFoci[name];
491     }
492     return NULL;
493 }
494
495 void printAllResources()
496 {
497     for(unsigned i=0; i < resource::resources.size(); i++){
498         printf("{");
499         (resource::resources[i])->print();
500         printf("}");
501         printf("\n");
502     }
503 }