Added a buffer to each process structure to allow for multiple writers on the
[dyninst.git] / paradynd / src / main.C
1 /*
2  * Main loop for the default paradynd.
3  *
4  * $Log: main.C,v $
5  * Revision 1.6  1994/03/20 01:53:09  markc
6  * Added a buffer to each process structure to allow for multiple writers on the
7  * traceStream.  Replaced old inst-pvm.C.  Changed addProcess to return type
8  * int.
9  *
10  * Revision 1.5  1994/02/28  05:09:42  markc
11  * Added pvm hooks and ifdefs.
12  *
13  * Revision 1.4  1994/02/25  13:40:55  markc
14  * Added hooks for pvm support.
15  *
16  * Revision 1.3  1994/02/24  04:32:33  markc
17  * Changed header files to reflect igen changes.  main.C does not look at the number of command line arguments now.
18  *
19  * Revision 1.2  1994/02/01  18:46:52  hollings
20  * Changes for adding perfConsult thread.
21  *
22  * Revision 1.1  1994/01/27  20:31:27  hollings
23  * Iinital version of paradynd speaking dynRPC igend protocol.
24  *
25  *
26  */
27 #include <stdio.h>
28 #include <stdlib.h>
29 #include <sys/types.h>
30 #include <sys/time.h>
31 #include <assert.h>
32
33 #include "util/h/list.h"
34 #include "rtinst/h/rtinst.h"
35
36 #include "symtab.h"
37 #include "process.h"
38 #include "inst.h"
39 #include "instP.h"
40 #include "ast.h"
41 #include "util.h"
42 #include "dyninstP.h"
43 #include "metric.h"
44 #include "dyninstRPC.SRVR.h"
45
46 dynRPC *tp;
47 extern void controllerMainLoop();
48 extern void initLibraryFunctions();
49
50 #ifdef PARADYND_PVM
51 static dynRPC *init_pvm_code(char *argv[], char *machine, int family,
52                              int type, int well_known_socket, int flag);
53 #endif     
54
55 main(int argc, char *argv[])
56 {
57     int i, family, type, well_known_socket, flag;
58     char *machine;
59     metricList stuff;
60
61     initLibraryFunctions();
62
63     // process command line args passed in
64     // flag == 1 --> started by paradyn
65     assert (RPC_undo_arg_list (argc, argv, &machine, family, type,
66                        well_known_socket, flag) == 0);
67
68 #ifdef PARADYND_PVM
69     tp = init_pvm_code(argv, machine, family, type, well_known_socket, flag);
70 #else
71     tp = new dynRPC(0, NULL, NULL);
72 #endif
73
74     //
75     // tell client about our metrics.
76     //
77     stuff = getMetricList();
78     for (i=0; i < stuff->count; i++) {
79         tp->newMetricCallback(stuff->elements[i].info);
80     }
81
82     controllerMainLoop();
83 }
84
85 void dynRPC::addResource(String parent, String name)
86 {
87     resource pr;
88     extern resource findResource(char*);
89
90     pr = findResource(parent);
91     if (pr) (void) newResource(pr, NULL, name, 0.0);
92 }
93
94 void dynRPC::coreProcess(int pid)
95 {
96     process *proc;
97
98     proc = processList.find((void *) pid);
99     dumpCore(proc);
100 }
101
102 String dynRPC::getStatus(int pid)
103 {
104     process *proc;
105     extern char *getProcessStatus(process *proc);
106     char ret[50];
107
108     proc = processList.find((void *) pid);
109
110     if (!proc) {
111         sprintf (ret, "PID:%d not found for getStatus\n", pid);
112         return (ret);
113     }
114     else
115         return(getProcessStatus(proc));
116 }
117
118 //
119 // NOTE: This version of getAvailableMetrics assumes that new metrics are
120 //   NOT added during execution.
121 //
122 metricInfo_Array dynRPC::getAvailableMetrics(void)
123 {
124     int i;
125     static int inited;
126     static metricInfo_Array metInfo;
127
128     if (!inited) {
129         metricList stuff;
130
131         stuff = getMetricList();
132         metInfo.count = stuff->count;
133         metInfo.data = (metricInfo*) calloc(sizeof(metricInfo), metInfo.count);
134         for (i=0; i < metInfo.count; i++) {
135             metInfo.data[i] = stuff->elements[i].info;
136         }
137         inited = 1;
138     }
139     return(metInfo);
140 }
141
142 double dynRPC::getPredictedDataCost(String_Array focusString, String metric)
143 {
144     metric m;
145     double val;
146     resourceList l;
147
148     m = findMetric(metric);
149     l = findFocus(focusString.count, focusString.data);
150     if (!l) return(0.0);
151     val = guessCost(l, m);
152
153     return(val);
154 }
155
156 void dynRPC::disableDataCollection(int mid)
157 {
158     metricInstance mi;
159     extern void printResourceList(resourceList);
160
161     printf("disable of %s for RL =", getMetricName(mi->met));
162     printResourceList(mi->resList);
163     printf("\n");
164
165     mi = allMIs.find((void *) mid);
166     mi->disable();
167     allMIs.remove(mi);
168     delete(mi);
169 }
170
171 int dynRPC::enableDataCollection(String_Array foucsString,String metric)
172 {
173     int id;
174     metric m;
175     resourceList l;
176
177     m = findMetric(metric);
178     l = findFocus(foucsString.count, foucsString.data);
179     if (!l) return(-1);
180     id = startCollecting(l, m);
181     return(id);
182 }
183
184 //
185 // not implemented yet.
186 //
187 void dynRPC::setSampleRate(double sampleInterval)
188 {
189     return;
190 }
191
192 Boolean dynRPC::detachProgram(int program,Boolean pause)
193 {
194     return(detachProcess(program, pause));
195 }
196
197 //
198 // Continue program.  We really should make this work on a single pid.
199 //
200 void dynRPC::continueProgram(int program)
201 {
202     continueApplication();
203 }
204 //
205 // We really should make this work on a single pid.
206 //
207 Boolean dynRPC::pauseProgram(int program)
208 {
209     return(pauseApplication());
210 }
211
212 Boolean dynRPC::startProgram(int program)
213 {
214     continueApplication();
215     return(False);
216 }
217
218 //
219 // This is not implemented yet.
220 //
221 Boolean dynRPC::attachProgram(int pid)
222 {
223     return(FALSE);
224 }
225
226 //
227 // start a new program for the tool.
228 //
229 int dynRPC::addExecutable(int argc,String_Array argv)
230 {
231     return(addProcess(argc, argv.data));
232 }
233
234 #ifdef PARADYND_PVM
235 dynRPC *
236 init_pvm_code(char *argv[], char *machine, int family,
237               int type, int well_known_socket, int flag)
238 {
239   dynRPC *temp;
240
241   extern int PDYN_initForPVM (char **, char *, int, int, int, int);
242
243   assert(PDYN_initForPVM (argv, machine, family, type, well_known_socket,
244                          flag) == 0);
245
246   // connect to paradyn
247   if (flag == 1)
248     temp = new dynRPC(0, NULL, NULL);
249   else
250     {
251       temp = new dynRPC(family, well_known_socket, type, machine, NULL, NULL);
252       temp->reportSelf (machine, argv[0], getpid());
253     }
254
255     return temp;
256 }
257 #endif
258