~ubuntu-branches/ubuntu/hardy/openmpi/hardy-updates

« back to all changes in this revision

Viewing changes to opal/mca/base/mca_base_components_open.c

  • Committer: Bazaar Package Importer
  • Author(s): Mark Hymers
  • Date: 2006-10-15 00:46:11 UTC
  • Revision ID: james.westby@ubuntu.com-20061015004611-uuhxnaxyjmuxfd5h
Tags: upstream-1.1
ImportĀ upstreamĀ versionĀ 1.1

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/*
 
2
 * Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
 
3
 *                         University Research and Technology
 
4
 *                         Corporation.  All rights reserved.
 
5
 * Copyright (c) 2004-2005 The University of Tennessee and The University
 
6
 *                         of Tennessee Research Foundation.  All rights
 
7
 *                         reserved.
 
8
 * Copyright (c) 2004-2005 High Performance Computing Center Stuttgart, 
 
9
 *                         University of Stuttgart.  All rights reserved.
 
10
 * Copyright (c) 2004-2005 The Regents of the University of California.
 
11
 *                         All rights reserved.
 
12
 * $COPYRIGHT$
 
13
 * 
 
14
 * Additional copyrights may follow
 
15
 * 
 
16
 * $HEADER$
 
17
 */
 
18
 
 
19
#include "opal_config.h"
 
20
 
 
21
#include <stdio.h>
 
22
#include <string.h>
 
23
#include <stdlib.h>
 
24
 
 
25
#include "opal/class/opal_list.h"
 
26
#include "opal/util/strncpy.h"
 
27
#include "opal/util/argv.h"
 
28
#include "opal/util/output.h"
 
29
#include "opal/util/show_help.h"
 
30
#include "opal/mca/mca.h"
 
31
#include "opal/mca/base/base.h"
 
32
#include "opal/mca/base/mca_base_component_repository.h"
 
33
#include "opal/constants.h"
 
34
 
 
35
struct component_name_t {
 
36
  opal_list_item_t super;
 
37
 
 
38
  char mn_name[MCA_BASE_MAX_COMPONENT_NAME_LEN];
 
39
};
 
40
typedef struct component_name_t component_name_t;
 
41
 
 
42
 
 
43
/*
 
44
 * Local variables
 
45
 */
 
46
static bool show_errors = false;
 
47
static const char negate = '^';
 
48
 
 
49
 
 
50
/*
 
51
 * Local functions
 
52
 */
 
53
static int parse_requested(int mca_param, bool *include_mode,
 
54
                           char ***requested_component_names);
 
55
static int open_components(const char *type_name, int output_id, 
 
56
                           opal_list_t *src, opal_list_t *dest);
 
57
static int distill(bool include_mode, const char *type_name,
 
58
                   int output_id, opal_list_t *src, opal_list_t *dest,
 
59
                   char **names);
 
60
 
 
61
 
 
62
/**
 
63
 * Function for finding and opening either all MCA components, or the
 
64
 * one that was specifically requested via a MCA parameter.
 
65
 */
 
66
int mca_base_components_open(const char *type_name, int output_id,
 
67
                             const mca_base_component_t **static_components,
 
68
                             opal_list_t *components_available,
 
69
                             bool open_dso_components)
 
70
{
 
71
  int ret, param;
 
72
  opal_list_item_t *item;
 
73
  opal_list_t components_found, components_distilled;
 
74
  char **requested_component_names;
 
75
  int param_verbose = -1;
 
76
  int param_type = -1;
 
77
  int verbose_level;
 
78
  char *str;
 
79
  bool include_mode;
 
80
  bool distilled = false;
 
81
 
 
82
  /* Register MCA parameters */
 
83
 
 
84
  asprintf(&str, "Default selection set of components for the %s framework (<none> means \"use all components that can be found\")", type_name);
 
85
  param_type = 
 
86
      mca_base_param_reg_string_name(type_name, NULL, str, 
 
87
                                     false, false, NULL, NULL);
 
88
  free(str);
 
89
 
 
90
  asprintf(&str, "Verbosity level for the %s framework (0 = no verbosity)", type_name);
 
91
  param_verbose = 
 
92
      mca_base_param_reg_int_name(type_name, "base_verbose",
 
93
                                  str, false, false, 0, NULL);
 
94
  free(str);
 
95
 
 
96
  param = mca_base_param_find("mca", NULL, "component_show_load_errors");
 
97
  mca_base_param_lookup_int(param, &ret);
 
98
  show_errors = (0 != ret) ? true : false;
 
99
 
 
100
  /* Setup verbosity for this MCA type */
 
101
 
 
102
  mca_base_param_lookup_int(param_verbose, &verbose_level);
 
103
  if (output_id != 0) {
 
104
    opal_output_set_verbosity(output_id, verbose_level);
 
105
  }
 
106
  opal_output_verbose(10, output_id, 
 
107
                      "mca: base: components_open: Looking for %s components",
 
108
                      type_name);
 
109
 
 
110
  /* Find and load all available components */
 
111
 
 
112
  if (OPAL_SUCCESS != 
 
113
      mca_base_component_find(NULL, type_name, static_components,
 
114
                              &components_found, open_dso_components)) {
 
115
    return OPAL_ERROR;
 
116
  }
 
117
 
 
118
  /* See if one or more specific components were requested */
 
119
 
 
120
  ret = parse_requested(param_type, &include_mode, &requested_component_names);
 
121
  if (OPAL_SUCCESS == ret) {
 
122
      ret = distill(include_mode, type_name, output_id, &components_found,
 
123
                    &components_distilled, requested_component_names);
 
124
      distilled = true;
 
125
  }
 
126
 
 
127
  /* Now open whatever we have left */
 
128
 
 
129
  if (OPAL_SUCCESS == ret) {
 
130
      ret = open_components(type_name, output_id,
 
131
                            &components_distilled, components_available);
 
132
  }
 
133
 
 
134
  /* Free resources */
 
135
 
 
136
  for (item = opal_list_remove_first(&components_found); NULL != item;
 
137
       item = opal_list_remove_first(&components_found)) {
 
138
      OBJ_RELEASE(item);
 
139
  }
 
140
  OBJ_DESTRUCT(&components_found);
 
141
  if (distilled) {
 
142
      for (item = opal_list_remove_first(&components_distilled); NULL != item;
 
143
           item = opal_list_remove_first(&components_distilled)) {
 
144
          OBJ_RELEASE(item);
 
145
      }
 
146
      OBJ_DESTRUCT(&components_distilled);
 
147
  }
 
148
  if (NULL != requested_component_names) {
 
149
      opal_argv_free(requested_component_names);
 
150
  }
 
151
 
 
152
  /* All done */
 
153
 
 
154
  return ret;
 
155
}
 
156
 
 
157
 
 
158
static int parse_requested(int mca_param, bool *include_mode,
 
159
                           char ***requested_component_names)
 
160
{
 
161
  int i;
 
162
  char *requested;
 
163
  char *tmp;
 
164
 
 
165
  *requested_component_names = NULL;
 
166
  *include_mode = true;
 
167
 
 
168
  /* See if the user requested anything */
 
169
 
 
170
  if (OPAL_ERROR == mca_base_param_lookup_string(mca_param, &requested)) {
 
171
    return OPAL_ERROR;
 
172
  }
 
173
  if (NULL == requested || 0 == strlen(requested)) {
 
174
    return OPAL_SUCCESS;
 
175
  }
 
176
  *requested_component_names = opal_argv_split(requested, ',');
 
177
 
 
178
  /* Are we including or excluding? */
 
179
 
 
180
  for (i = 0; NULL != (*requested_component_names)[i]; ++i) {
 
181
      if (negate == *((*requested_component_names)[i])) {
 
182
          tmp = strdup((*requested_component_names)[i] + 1);
 
183
          free((*requested_component_names)[i]);
 
184
          (*requested_component_names)[i] = tmp;
 
185
 
 
186
          *include_mode = false;
 
187
      }
 
188
  }
 
189
 
 
190
  /* All done */
 
191
 
 
192
  return OPAL_SUCCESS;
 
193
}
 
194
 
 
195
 
 
196
/*
 
197
 * Parse the list of found components and factor in the included /
 
198
 * excluded names to come up with a distilled list of components that
 
199
 * we should try to open.
 
200
 */
 
201
static int distill(bool include_mode, const char *type_name,
 
202
                   int output_id, opal_list_t *src, opal_list_t *dest,
 
203
                   char **names)
 
204
{
 
205
    int i;
 
206
    bool good;
 
207
    opal_list_item_t *item, *next;
 
208
    const mca_base_component_t *component;
 
209
    mca_base_component_list_item_t *cli;
 
210
 
 
211
    opal_output_verbose(10, output_id,
 
212
                        "mca: base: components_open: "
 
213
                        "distilling %s components", type_name);
 
214
    OBJ_CONSTRUCT(dest, opal_list_t);
 
215
 
 
216
    /* Bozo case */
 
217
 
 
218
    if (NULL == names) {
 
219
        opal_output_verbose(10, output_id,
 
220
                            "mca: base: components_open: "
 
221
                            "accepting all %s components", type_name);
 
222
        opal_list_join(dest, opal_list_get_end(dest), src);
 
223
        return OPAL_SUCCESS;
 
224
    }
 
225
 
 
226
    /* Are we including components? */
 
227
 
 
228
    if (include_mode) {
 
229
        opal_output_verbose(10, output_id,
 
230
                            "mca: base: components_open: "
 
231
                            "including %s components", type_name);
 
232
 
 
233
        /* Go through all the components and only keep the ones that
 
234
           are specifically mentioned in the list */
 
235
 
 
236
        for (i = 0; NULL != names[i]; ++i) {
 
237
            good = false;
 
238
 
 
239
            for (item = opal_list_get_first(src);
 
240
                 opal_list_get_end(src) != item;
 
241
                 item = next) {
 
242
                next = opal_list_get_next(item);
 
243
                cli = (mca_base_component_list_item_t *) item;
 
244
                component = cli->cli_component;
 
245
                if (0 == strcmp(names[i], component->mca_component_name)) {
 
246
                    opal_list_remove_item(src, item);
 
247
                    opal_list_append(dest, item);
 
248
                    good = true;
 
249
                    break;
 
250
                }
 
251
            }
 
252
 
 
253
            if (good) {
 
254
                opal_output_verbose(10, output_id, 
 
255
                                    "mca: base: components_open:   "
 
256
                                    "%s --> included", names[i]);
 
257
            } else {
 
258
                opal_output_verbose(10, output_id, 
 
259
                                    "mca: base: components_open:   "
 
260
                                    "%s --> not found", names[i]);
 
261
            }
 
262
        }
 
263
    }
 
264
 
 
265
    /* No, we are excluding components */
 
266
   
 
267
    else {
 
268
        opal_output_verbose(10, output_id,
 
269
                            "mca: base: components_open: "
 
270
                            "excluding %s components", type_name);
 
271
 
 
272
        /* Go through all the components and only keep the ones that
 
273
           are specifically mentioned in the list */
 
274
 
 
275
        for (item = opal_list_get_first(src);
 
276
             opal_list_get_end(src) != item;
 
277
             item = next) {
 
278
            next = opal_list_get_next(item);
 
279
            good = true;
 
280
            cli = (mca_base_component_list_item_t *) item;
 
281
            component = cli->cli_component;
 
282
 
 
283
            for (i = 0; NULL != names[i]; ++i) {
 
284
                if (0 == strcmp(names[i], component->mca_component_name)) {
 
285
                    good = false;
 
286
                    break;
 
287
                }
 
288
            }
 
289
 
 
290
            if (!good) {
 
291
                opal_output_verbose(10, output_id, 
 
292
                                    "mca: base: components_open:   "
 
293
                                    "%s --> excluded", 
 
294
                                    component->mca_component_name);
 
295
            } else {
 
296
                opal_list_remove_item(src, item);
 
297
                opal_list_append(dest, item);
 
298
                opal_output_verbose(10, output_id, 
 
299
                                    "mca: base: components_open:   "
 
300
                                    "%s --> included",
 
301
                                    component->mca_component_name);
 
302
            }
 
303
        }
 
304
    }
 
305
 
 
306
    /* All done */
 
307
 
 
308
    return OPAL_SUCCESS;
 
309
}
 
310
 
 
311
 
 
312
/*
 
313
 * Traverse the entire list of found components (a list of
 
314
 * mca_base_component_t instances).  If the requested_component_names
 
315
 * array is empty, or the name of each component in the list of found
 
316
 * components is in the requested_components_array, try to open it.
 
317
 * If it opens, add it to the components_available list.
 
318
 */
 
319
static int open_components(const char *type_name, int output_id, 
 
320
                           opal_list_t *src, opal_list_t *dest)
 
321
{
 
322
    opal_list_item_t *item;
 
323
    const mca_base_component_t *component;
 
324
    mca_base_component_list_item_t *cli;
 
325
    bool called_open;
 
326
    bool opened;
 
327
    
 
328
    /* Announce */
 
329
    
 
330
    opal_output_verbose(10, output_id,
 
331
                        "mca: base: components_open: opening %s components",
 
332
                        type_name);
 
333
    
 
334
    /* Traverse the list of found components */
 
335
    
 
336
    OBJ_CONSTRUCT(dest, opal_list_t);
 
337
    for (item = opal_list_get_first(src);
 
338
         opal_list_get_end(src) != item;
 
339
         item = opal_list_get_next(item)) {
 
340
        cli = (mca_base_component_list_item_t *) item;
 
341
        component = cli->cli_component;
 
342
        
 
343
        opened = called_open = false;
 
344
        opal_output_verbose(10, output_id, 
 
345
                            "mca: base: components_open: found loaded component %s",
 
346
                            component->mca_component_name);
 
347
        
 
348
        if (NULL == component->mca_open_component) {
 
349
            opened = true; 
 
350
            opal_output_verbose(10, output_id, 
 
351
                                "mca: base: components_open: "
 
352
                                "component %s has no open function",
 
353
                                component->mca_component_name);
 
354
        } else {
 
355
            called_open = true;
 
356
            if (MCA_SUCCESS == component->mca_open_component()) {
 
357
                opened = true;
 
358
                opal_output_verbose(10, output_id, 
 
359
                                    "mca: base: components_open: "
 
360
                                    "component %s open function successful",
 
361
                                    component->mca_component_name);
 
362
            } else {
 
363
                /* We may end up displaying this twice, but it may go
 
364
                   to separate streams.  So better to be redundant
 
365
                   than to not display the error in the stream where
 
366
                   it was expected. */
 
367
                
 
368
                if (show_errors) {
 
369
                    opal_output(0, "mca: base: components_open: "
 
370
                                "component %s / %s open function failed",
 
371
                                component->mca_type_name,
 
372
                                component->mca_component_name);
 
373
                }
 
374
                opal_output_verbose(10, output_id, 
 
375
                                    "mca: base: components_open: "
 
376
                                    "component %s open function failed",
 
377
                                    component->mca_component_name);
 
378
            }
 
379
        }
 
380
        
 
381
        /* If it didn't open, close it out and get rid of it */
 
382
        
 
383
        if (!opened) {
 
384
            if (called_open) {
 
385
                if (NULL != component->mca_close_component) {
 
386
                    component->mca_close_component();
 
387
                }
 
388
                opal_output_verbose(10, output_id, 
 
389
                                    "mca: base: components_open: component %s closed",
 
390
                                    component->mca_component_name);
 
391
                called_open = false;
 
392
            }
 
393
            mca_base_component_repository_release(component);
 
394
            opal_output_verbose(10, output_id, 
 
395
                                "mca: base: components_open: component %s unloaded", 
 
396
                                component->mca_component_name);
 
397
        }
 
398
        
 
399
        /* If it did open, register its "priority" MCA parameter (if
 
400
           it doesn't already have one) and save it in the
 
401
           opened_components list */
 
402
        
 
403
        else {
 
404
            if (OPAL_ERROR == mca_base_param_find(type_name, 
 
405
                                                  component->mca_component_name,
 
406
                                                  "priority")) {
 
407
                mca_base_param_register_int(type_name,
 
408
                                            component->mca_component_name,
 
409
                                            "priority", NULL, 0);
 
410
            }
 
411
            
 
412
            cli = OBJ_NEW(mca_base_component_list_item_t);
 
413
            if (NULL == cli) {
 
414
                return OPAL_ERR_OUT_OF_RESOURCE;
 
415
            }
 
416
            cli->cli_component = component;
 
417
            opal_list_append(dest, (opal_list_item_t *) cli);
 
418
        }
 
419
    }
 
420
    
 
421
    /* All done */
 
422
    
 
423
    return OPAL_SUCCESS;
 
424
}