source: rtems/cpukit/libmisc/monitor/mon-server.c @ 77c4089

Last change on this file since 77c4089 was b9e230a2, checked in by Ralf Corsepius <ralf.corsepius@…>, on 07/08/03 at 08:38:15

2003-07-08 Ralf Corsepius <corsepiu@…>

  • capture/capture-cli.c: Add config-header support.
  • capture/capture.c: Add config-header support.
  • cpuuse/cpuuse.c: Add config-header support.
  • devnull/devnull.c: Add config-header support.
  • dummy/dummy.c: Add config-header support.
  • dumpbuf/dumpbuf.c: Add config-header support.
  • monitor/mon-command.c: Add config-header support.
  • monitor/mon-config.c: Add config-header support.
  • monitor/mon-dname.c: Add config-header support.
  • monitor/mon-driver.c: Add config-header support.
  • monitor/mon-extension.c: Add config-header support.
  • monitor/mon-itask.c: Add config-header support.
  • monitor/mon-manager.c: Add config-header support.
  • monitor/mon-monitor.c: Add config-header support.
  • monitor/mon-mpci.c: Add config-header support.
  • monitor/mon-object.c: Add config-header support.
  • monitor/mon-prmisc.c: Add config-header support.
  • monitor/mon-queue.c: Add config-header support.
  • monitor/mon-server.c: Add config-header support.
  • monitor/mon-symbols.c: Add config-header support.
  • monitor/mon-task.c: Add config-header support.
  • mw-fb/mw_fb.c: Add config-header support.
  • mw-fb/mw_uid.c: Add config-header support.
  • rtmonuse/rtmonuse.c: Add config-header support.
  • serdbg/serdbg.c: Add config-header support.
  • serdbg/serdbgio.c: Add config-header support.
  • serdbg/termios_printk.c: Add config-header support.
  • shell/cmds.c: Add config-header support.
  • stackchk/check.c: Add config-header support.
  • untar/untar.c: Add config-header support.
  • Property mode set to 100644
File size: 9.0 KB
Line 
1/*
2 * RTEMS monitor server (handles requests for info from RTEMS monitors
3 *             running on other nodes)
4 *
5 *  $Id$
6 */
7
8#ifdef HAVE_CONFIG_H
9#include "config.h"
10#endif
11
12#include <rtems.h>
13
14#include <stdio.h>
15#include <string.h>
16#include <stdlib.h>
17#include <unistd.h>
18
19#include <rtems/monitor.h>
20
21/*
22 * Various id's for the server
23 */
24
25rtems_id  rtems_monitor_server_task_id;
26rtems_id  rtems_monitor_server_request_queue_id;        /* our server */
27rtems_id *rtems_monitor_server_request_queue_ids;       /* all servers */
28rtems_id  rtems_monitor_server_response_queue_id;       /* our server */
29
30
31/*
32 * Send a request to a server task
33 */
34
35rtems_status_code
36rtems_monitor_server_request(
37    unsigned32                       server_node,
38    rtems_monitor_server_request_t  *request,
39    rtems_monitor_server_response_t *response
40)
41{
42    rtems_id          server_id;
43    rtems_status_code status;
44    unsigned32        size;
45
46    /*
47     * What is id of monitor on target node?
48     * Look it up if we don't know it yet.
49     */
50   
51    server_id = rtems_monitor_server_request_queue_ids[server_node];
52    if (server_id == 0)
53    {
54        status = rtems_message_queue_ident(RTEMS_MONITOR_QUEUE_NAME,
55                                           server_node,
56                                           &server_id);
57        if (status != RTEMS_SUCCESSFUL)
58        {
59            rtems_error(status, "ident of remote server failed");
60            goto done;
61        }
62       
63        rtems_monitor_server_request_queue_ids[server_node] = server_id;
64    }
65
66    request->return_id = rtems_monitor_server_response_queue_id;
67
68    status = rtems_message_queue_send(server_id, request, sizeof(*request));
69    if (status != RTEMS_SUCCESSFUL)
70    {
71        rtems_error(status, "monitor server request send failed");
72        goto done;
73    }
74   
75    /*
76     * Await response, if requested
77     */
78
79    if (response)
80    {
81        status = rtems_message_queue_receive(rtems_monitor_server_response_queue_id,
82                                             response,
83                                             &size,
84                                             RTEMS_WAIT,
85                                             100);
86        if (status != RTEMS_SUCCESSFUL)
87        {
88            rtems_error(status, "server did not respond");
89
90            /* maybe server task was restarted; look it up again next time */
91            rtems_monitor_server_request_queue_ids[server_node] = 0;
92
93            goto done;
94        }
95
96        if (response->command != RTEMS_MONITOR_SERVER_RESPONSE)
97        {
98            status = RTEMS_INCORRECT_STATE;
99            goto done;
100        }           
101    }
102   
103done:
104    return status;
105}
106
107
108
109/*
110 * monitor server task
111 */
112
113void
114rtems_monitor_server_task(
115    rtems_task_argument monitor_flags
116)
117{
118    rtems_monitor_server_request_t  request;
119    rtems_monitor_server_response_t response;
120    rtems_status_code               status;
121    unsigned32                      size;
122
123    for (;;)
124    {
125        status = rtems_message_queue_receive(
126                        rtems_monitor_server_request_queue_id,
127                        &request,
128                        &size,
129                        RTEMS_WAIT,
130                        (rtems_interval) 0);
131
132        if (status != RTEMS_SUCCESSFUL)
133        {
134            rtems_error(status, "monitor server msg queue receive error");
135            goto failed;
136        }
137                                             
138        if (size != sizeof(request))
139        {
140            rtems_error(0, "monitor server bad size on receive");
141            goto failed;
142        }
143       
144        switch (request.command)
145        {
146            case RTEMS_MONITOR_SERVER_CANONICAL:
147            {
148                rtems_monitor_object_type_t object_type;
149                rtems_id            id;
150                rtems_id            next_id;
151
152                object_type = (rtems_monitor_object_type_t) request.argument0;
153                id          = (rtems_id)            request.argument1;
154                next_id = rtems_monitor_object_canonical_get(object_type,
155                                                             id,
156                                                             &response.payload,
157                                                             &size);
158
159                response.command = RTEMS_MONITOR_SERVER_RESPONSE;
160                response.result0 = next_id;
161                response.result1 = size;
162
163#define SERVER_OVERHEAD  (RTEMS_offsetof(rtems_monitor_server_response_t, \
164                                         payload))
165                   
166                status = rtems_message_queue_send(request.return_id,
167                                                  &response,
168                                                  size + SERVER_OVERHEAD);
169                if (status != RTEMS_SUCCESSFUL)
170                {
171                    rtems_error(status, "response send failed");
172                    goto failed;
173                }
174                break;
175            }
176
177            default:
178            {
179                rtems_error(0, "invalid command to monitor server: %d", request.command);
180                goto failed;
181            }
182        }
183    }
184
185failed:
186    rtems_task_delete(RTEMS_SELF);
187}
188
189   
190/*
191 * Kill off any old server
192 * Not sure if this is useful, but it doesn't help
193 */
194
195void
196rtems_monitor_server_kill(void)
197{
198    if (rtems_monitor_server_task_id)
199        rtems_task_delete(rtems_monitor_server_task_id);
200    rtems_monitor_server_task_id = 0;
201
202    if (rtems_monitor_server_request_queue_id)
203        rtems_message_queue_delete(rtems_monitor_server_request_queue_id);
204    rtems_monitor_server_request_queue_ids = 0;
205
206    if (rtems_monitor_server_response_queue_id)
207        rtems_message_queue_delete(rtems_monitor_server_response_queue_id);
208    rtems_monitor_server_response_queue_id = 0;
209
210    if (rtems_monitor_server_request_queue_ids)
211        free(rtems_monitor_server_request_queue_ids);
212    rtems_monitor_server_request_queue_ids = 0;
213}
214
215
216void
217rtems_monitor_server_init(
218    unsigned32 monitor_flags
219)
220{
221    rtems_status_code status;
222   
223    if (_System_state_Is_multiprocessing    &&
224        (_Configuration_MP_table->maximum_nodes > 1))
225    {
226        unsigned32 maximum_nodes = _Configuration_MP_table->maximum_nodes;
227       
228        /*
229         * create the msg que our server will listen
230         * Since we only get msgs from other RTEMS monitors, we just
231         * need reserve space for 1 msg from each node.
232         */
233
234        status = rtems_message_queue_create(
235                       RTEMS_MONITOR_QUEUE_NAME,
236                       maximum_nodes,
237                       sizeof(rtems_monitor_server_request_t),
238                       RTEMS_GLOBAL,
239                       &rtems_monitor_server_request_queue_id);
240       
241        if (status != RTEMS_SUCCESSFUL)
242        {
243            rtems_error(status, "could not create monitor server message queue");
244            goto done;
245        }
246         
247        /*
248         * create the msg que our responses will come on
249         * Since monitor just does one thing at a time, we only need 1 item
250         * message queue.
251         */
252       
253        status = rtems_message_queue_create(
254                       RTEMS_MONITOR_RESPONSE_QUEUE_NAME,
255                       1, /* depth */
256                       sizeof(rtems_monitor_server_response_t),
257                       RTEMS_GLOBAL,
258                       &rtems_monitor_server_response_queue_id);
259       
260        if (status != RTEMS_SUCCESSFUL)
261        {
262            rtems_error(status, "could not create monitor response message queue");
263            goto done;
264        }
265         
266        /* need an id for queue of each other server we might talk to */
267        /* indexed by node, so add 1 to maximum_nodes */
268        rtems_monitor_server_request_queue_ids =
269                   (rtems_id *) malloc((maximum_nodes + 1) * sizeof(rtems_id));
270        (void) memset(rtems_monitor_server_request_queue_ids,
271                      0,
272                      (maximum_nodes + 1) * sizeof(rtems_id));
273
274        rtems_monitor_server_request_queue_ids[rtems_monitor_node] =
275                   rtems_monitor_server_request_queue_id;
276
277        /*
278         * create the server task
279         */
280        status = rtems_task_create(RTEMS_MONITOR_SERVER_NAME,
281                                   1,
282                                   0 /* default stack */,
283                                   RTEMS_INTERRUPT_LEVEL(0),
284                                   RTEMS_DEFAULT_ATTRIBUTES,
285                                   &rtems_monitor_server_task_id);
286        if (status != RTEMS_SUCCESSFUL)
287        {
288            rtems_error(status, "could not create monitor server task");
289            goto done;
290        }
291
292        /*
293         * Start the server task
294         */
295        status = rtems_task_start(rtems_monitor_server_task_id,
296                                  rtems_monitor_server_task,
297                                  monitor_flags);
298        if (status != RTEMS_SUCCESSFUL)
299        {
300            rtems_error(status, "could not start monitor server");
301            goto done;
302        }
303    }
304
305done:
306    return;
307}
Note: See TracBrowser for help on using the repository browser.