OpenCores
URL https://opencores.org/ocsvn/openrisc_me/openrisc_me/trunk

Subversion Repositories openrisc_me

[/] [openrisc/] [trunk/] [rtos/] [ecos-2.0/] [tools/] [src/] [tools/] [configtool/] [standalone/] [common/] [cdl_exec.cxx] - Blame information for rev 174

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 26 unneback
//####COPYRIGHTBEGIN####
2
//                                                                          
3
// ----------------------------------------------------------------------------
4
// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
5
// Copyright (C) 2003 John Dallaway
6
//
7
// This program is part of the eCos host tools.
8
//
9
// This program is free software; you can redistribute it and/or modify it 
10
// under the terms of the GNU General Public License as published by the Free 
11
// Software Foundation; either version 2 of the License, or (at your option) 
12
// any later version.
13
// 
14
// This program is distributed in the hope that it will be useful, but WITHOUT 
15
// ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 
16
// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for 
17
// more details.
18
// 
19
// You should have received a copy of the GNU General Public License along with
20
// this program; if not, write to the Free Software Foundation, Inc., 
21
// 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
22
//
23
// ----------------------------------------------------------------------------
24
//                                                                          
25
//####COPYRIGHTEND####
26
//==========================================================================
27
//
28
//      cdl_exec.cxx
29
//
30
//      The implementation of each ecosconfig command
31
//
32
//==========================================================================
33
//==========================================================================
34
//#####DESCRIPTIONBEGIN####                                             
35
//
36
// Author(s):           jld
37
// Date:                1999-11-08
38
//
39
//####DESCRIPTIONEND####
40
//==========================================================================
41
 
42
#ifdef _MSC_VER
43
#include <direct.h> /* for getcwd() */
44
#else
45
#include <unistd.h> /* for getcwd() */
46
#endif
47
#ifdef __CYGWIN__
48
#include <windows.h>
49
#include <sys/param.h>  /* for MAXPATHLEN */
50
#include <sys/cygwin.h> /* for cygwin_conv_to_win32_path() */
51
#endif
52
#include "build.hxx"
53
#include "cdl_exec.hxx"
54
 
55
// ----------------------------------------------------------------------------
56
bool cdl_exec::quiet            = false;
57
bool cdl_exec::verbose          = false;
58
bool cdl_exec::ignore_errors    = false;
59
bool cdl_exec::no_updates       = false;
60
bool cdl_exec::debug_level_set  = false;
61
int  cdl_exec::debug_level      = 0;
62
 
63
cdl_exec::cdl_exec (const std::string repository_arg, const std::string savefile_arg,
64
                    const std::string install_arg, bool no_resolve_arg)
65
    : repository(repository_arg),
66
      savefile(savefile_arg),
67
      install_prefix(install_arg),
68
      no_resolve(no_resolve_arg),
69
      pkgdata (NULL),
70
      interp (NULL),
71
      config (NULL)
72
{
73
 
74
    // The inference callback does not actually do anything at present.
75
    // In future it may be useful for diagnostic purposes.
76
    CdlTransactionBody::set_inference_callback_fn (&inference_callback);
77
 
78
    // Automatic inference is always disabled. The inference engine
79
    // only gets invoked explicitly, after a suitable transaction callback
80
    // has been invoked. The problem here is that the transaction callback
81
    // has to report changes made by the inference engine but there is
82
    // no way of distinguishing between inferred values that come out of
83
    // savefiles and inferred values determined by the inference engine.
84
    CdlTransactionBody::disable_automatic_inference ();
85
}
86
 
87
void
88
cdl_exec::set_quiet_mode(bool new_val)
89
{
90
    quiet = new_val;
91
}
92
 
93
void
94
cdl_exec::set_verbose_mode(bool new_val)
95
{
96
    verbose = new_val;
97
    CdlPackagesDatabaseBody::set_verbose(new_val);
98
}
99
 
100
void
101
cdl_exec::set_ignore_errors_mode(bool new_val)
102
{
103
    ignore_errors = new_val;
104
}
105
 
106
void
107
cdl_exec::set_no_updates_mode(bool new_val)
108
{
109
    no_updates = new_val;
110
}
111
 
112
void
113
cdl_exec::set_debug_level(int new_level)
114
{
115
    debug_level_set = true;
116
    debug_level = new_level;
117
}
118
 
119
// ----------------------------------------------------------------------------
120
void
121
cdl_exec::init(bool load_config)
122
{
123
    pkgdata = CdlPackagesDatabaseBody::make(repository, &diagnostic_handler, &diagnostic_handler);
124
    interp  = CdlInterpreterBody::make();
125
    if (load_config) {
126
        config = CdlConfigurationBody::load (savefile, pkgdata, interp, &diagnostic_handler, &diagnostic_handler);
127
    }
128
}
129
 
130
// ----------------------------------------------------------------------------
131
void
132
cdl_exec::delete_cdl_data ()
133
{
134
    if (0 != config) {
135
        delete config;
136
        config = 0;
137
    }
138
    if (0 != interp) {
139
        delete interp;
140
        interp = 0;
141
    }
142
    if (0 != pkgdata) {
143
        delete pkgdata;
144
        pkgdata = 0;
145
    }
146
}
147
 
148
// ----------------------------------------------------------------------------
149
bool cdl_exec::cmd_new (const std::string cdl_hardware,
150
                        const std::string cdl_template /* = "default" */,
151
                        const std::string cdl_version /* = "" */)
152
{
153
    bool status = false;
154
    try {
155
        init(false);
156
 
157
        config = CdlConfigurationBody::make ("eCos", pkgdata, interp);
158
 
159
        // The hardware and template should be loaded in a single transaction.
160
        // Validating the target name etc. can be left to libcdl.
161
        CdlLocalTransaction transact(config);
162
        config->set_hardware(transact.get(), resolve_hardware_alias(cdl_hardware), &diagnostic_handler, &diagnostic_handler);
163
        config->set_template(transact.get(), cdl_template, cdl_version, &diagnostic_handler, &diagnostic_handler);
164
        transact.body();
165
        transact.destroy();
166
 
167
        if (debug_level_set) {
168
            this->update_debug_level();
169
        }
170
 
171
        // Unless inference has been suppressed, make sure that the
172
        // inference engine gets invoked and that its results get
173
        // reported.
174
        if (!no_resolve) {
175
            CdlTransactionBody::set_callback_fn(&transaction_callback);
176
            config->resolve_all_conflicts();
177
        }
178
 
179
        // Now report any conflicts which the inference engine could not report. 
180
        report_conflicts();
181
 
182
        // A savefile should be generated/updated even if there are conflicts.
183
        // Otherwise the user does not have a chance to edit the savefile
184
        // and fix things.
185
        if (!no_updates) {
186
            config->save (savefile);
187
        }
188
        if (ignore_errors || (0 == config->get_all_conflicts().size())) {
189
            status = true;
190
        }
191
    } catch (CdlStringException exception) {
192
        exception_handler (exception);
193
    } catch (...) {
194
        exception_handler ();
195
    }
196
 
197
    delete_cdl_data ();
198
    return status;
199
}
200
 
201
// ----------------------------------------------------------------------------
202
bool
203
cdl_exec::cmd_target (const std::string cdl_target)
204
{
205
    bool status = false;
206
    try {
207
        init(true);
208
        config->set_hardware (resolve_hardware_alias (cdl_target), &diagnostic_handler, &diagnostic_handler);
209
        if (debug_level_set) {
210
            this->update_debug_level();
211
        }
212
        if (!no_resolve) {
213
            CdlTransactionBody::set_callback_fn(&transaction_callback);
214
            config->resolve_all_conflicts();
215
        }
216
        report_conflicts();
217
        if (!no_updates) {
218
            config->save (savefile);
219
        }
220
        if (ignore_errors || (0 == config->get_all_conflicts().size())) {
221
            status = true;
222
        }
223
    } catch (CdlStringException exception) {
224
        exception_handler (exception);
225
    } catch (...) {
226
        exception_handler ();
227
    }
228
 
229
    delete_cdl_data ();
230
    return status;
231
}
232
 
233
// ----------------------------------------------------------------------------
234
bool
235
cdl_exec::cmd_template (const std::string cdl_template, const std::string cdl_version /* = "" */)
236
{
237
    bool status = false;
238
    try {
239
        init(true);
240
        config->set_template (cdl_template, cdl_version, &diagnostic_handler, &diagnostic_handler);
241
        if (debug_level_set) {
242
            this->update_debug_level();
243
        }
244
        if (!no_resolve) {
245
            CdlTransactionBody::set_callback_fn(&transaction_callback);
246
            config->resolve_all_conflicts();
247
        }
248
        report_conflicts();
249
        if (!no_updates) {
250
            config->save (savefile);
251
        }
252
        if (ignore_errors || (0 == config->get_all_conflicts().size())) {
253
            status = true;
254
        }
255
    } catch (CdlStringException exception) {
256
        exception_handler (exception);
257
    } catch (...) {
258
        exception_handler ();
259
    }
260
 
261
    delete_cdl_data ();
262
    return status;
263
}
264
 
265
// ----------------------------------------------------------------------------
266
bool
267
cdl_exec::cmd_export (const std::string cdl_savefile)
268
{
269
    bool status = false;
270
    try {
271
        init(true);
272
        if (debug_level_set) {
273
            this->update_debug_level();
274
        }
275
        if (!no_resolve) {
276
            CdlTransactionBody::set_callback_fn(&transaction_callback);
277
            config->resolve_all_conflicts();
278
        }
279
        report_conflicts();
280
        // Exporting to another file should only happen if the
281
        // configuration is conflict-free. This is different from
282
        // updating the savefile.
283
        if (ignore_errors || (0 == config->get_all_conflicts().size())) {
284
            if (!no_updates) {
285
                config->save (cdl_savefile, /* minimal = */ true);
286
            }
287
            status = true;
288
        }
289
    } catch (CdlStringException exception) {
290
        exception_handler (exception);
291
    } catch (...) {
292
        exception_handler ();
293
    }
294
 
295
    delete_cdl_data ();
296
    return status;
297
}
298
 
299
// ----------------------------------------------------------------------------
300
bool
301
cdl_exec::cmd_import (const std::string cdl_savefile)
302
{
303
    bool status = false;
304
    try {
305
        init(true);
306
        config->add(cdl_savefile, &diagnostic_handler, &diagnostic_handler);
307
        if (debug_level_set) {
308
            this->update_debug_level();
309
        }
310
        if (!no_resolve) {
311
            CdlTransactionBody::set_callback_fn(&transaction_callback);
312
            config->resolve_all_conflicts();
313
        }
314
        report_conflicts();
315
        if (!no_updates) {
316
            config->save (savefile);
317
        }
318
        if (ignore_errors || (0 == config->get_all_conflicts().size())) {
319
            status = true;
320
        }
321
    } catch (CdlStringException exception) {
322
        exception_handler (exception);
323
    } catch (...) {
324
        exception_handler ();
325
    }
326
 
327
    delete_cdl_data ();
328
    return status;
329
}
330
 
331
// ----------------------------------------------------------------------------
332
bool
333
cdl_exec::cmd_add (const std::vector<std::string> cdl_packages)
334
{
335
    bool status = false;
336
    try {
337
        init(true);
338
        for (unsigned int n = 0; n < cdl_packages.size (); n++) {
339
            config->load_package (resolve_package_alias (cdl_packages [n]), "", &diagnostic_handler, &diagnostic_handler);
340
        }
341
        if (debug_level_set) {
342
            this->update_debug_level();
343
        }
344
        if (!no_resolve) {
345
            CdlTransactionBody::set_callback_fn(&transaction_callback);
346
            config->resolve_all_conflicts();
347
        }
348
        report_conflicts();
349
        if (!no_updates) {
350
            config->save (savefile);
351
        }
352
        if (ignore_errors || (0 == config->get_all_conflicts().size())) {
353
            status = true;
354
        }
355
    } catch (CdlStringException exception) {
356
        exception_handler (exception);
357
    } catch (...) {
358
        exception_handler ();
359
    }
360
 
361
    delete_cdl_data ();
362
    return status;
363
}
364
 
365
// ----------------------------------------------------------------------------
366
bool
367
cdl_exec::cmd_remove (const std::vector<std::string> cdl_packages)
368
{
369
    unsigned int n;
370
    bool status = false;
371
    try {
372
        init(true);
373
        for (n = 0; n < cdl_packages.size (); n++) {
374
            if (! config->lookup (resolve_package_alias (cdl_packages [n]))) {
375
                throw CdlStringException ("Unknown package " + cdl_packages [n]);
376
            }
377
        }
378
        for (n = 0; n < cdl_packages.size (); n++) {
379
            config->unload_package (resolve_package_alias (cdl_packages [n]));
380
        }
381
        if (debug_level_set) {
382
            this->update_debug_level();
383
        }
384
        if (!no_resolve) {
385
            CdlTransactionBody::set_callback_fn(&transaction_callback);
386
            config->resolve_all_conflicts();
387
        }
388
        report_conflicts();
389
        if (!no_updates) {
390
            config->save (savefile);
391
        }
392
        if (ignore_errors || (0 == config->get_all_conflicts().size())) {
393
            status = true;
394
        }
395
    } catch (CdlStringException exception) {
396
        exception_handler (exception);
397
    } catch (...) {
398
        exception_handler ();
399
    }
400
 
401
    delete_cdl_data ();
402
    return status;
403
}
404
 
405
// ----------------------------------------------------------------------------
406
bool
407
cdl_exec::cmd_version (const std::string cdl_version, const std::vector<std::string> cdl_packages)
408
{
409
    bool status = false;
410
    try {
411
        init(true);
412
        for (unsigned int n = 0; n < cdl_packages.size (); n++) {
413
            config->change_package_version(resolve_package_alias (cdl_packages [n]), cdl_version,
414
                                           &diagnostic_handler, &diagnostic_handler, true);
415
        }
416
        if (debug_level_set) {
417
            this->update_debug_level();
418
        }
419
        if (!no_resolve) {
420
            CdlTransactionBody::set_callback_fn(&transaction_callback);
421
            config->resolve_all_conflicts();
422
        }
423
        report_conflicts();
424
        if (!no_updates) {
425
            config->save (savefile);
426
        }
427
        if (ignore_errors || (0 == config->get_all_conflicts().size())) {
428
            status = true;
429
        }
430
    } catch (CdlStringException exception) {
431
        exception_handler (exception);
432
    } catch (...) {
433
        exception_handler ();
434
    }
435
 
436
    delete_cdl_data ();
437
    return status;
438
}
439
 
440
// ----------------------------------------------------------------------------
441
bool
442
cdl_exec::cmd_tree ()
443
{
444
    bool status = false;
445
    try {
446
        init(true);
447
        if (debug_level_set) {
448
            this->update_debug_level();
449
        }
450
        if (!no_resolve) {
451
            CdlTransactionBody::set_callback_fn(&transaction_callback);
452
            config->resolve_all_conflicts();
453
        }
454
        report_conflicts();
455
        if (!no_updates) {
456
            config->save (savefile);
457
        }
458
        // A build tree should only be generated if there are no conflicts,
459
        // and suppressed if -n is given.
460
        if (no_updates) {
461
            // Do nothing
462
        }
463
        else if (ignore_errors || (0 == config->get_all_conflicts().size())) {
464
#ifdef _MSC_VER
465
            char cwd [_MAX_PATH + 1];
466
#else
467
            char cwd [PATH_MAX + 1];
468
#endif
469
            getcwd (cwd, sizeof cwd);
470
#ifdef __CYGWIN__
471
            char cwd_win32 [MAXPATHLEN + 1];
472
            cygwin_conv_to_win32_path (cwd, cwd_win32);
473
            generate_build_tree (config, cwd_win32, install_prefix);
474
#else
475
            generate_build_tree (config, cwd, install_prefix);
476
#endif
477
            config->generate_config_headers (install_prefix.empty () ? "install/include/pkgconf" : install_prefix + "/include/pkgconf");
478
            status = true;
479
#ifdef __CYGWIN__
480
            char buf[100];
481
            strcpy(buf, "mount.exe -f -t -u x: /ecos-x");
482
            //printf("Cwd_win32: %s\n", cwd_win32);
483
 
484
            if ( cwd_win32[1] == ':' )
485
            {
486
                buf[19] = tolower(cwd_win32[0]);
487
                buf[28] = tolower(cwd_win32[0]);
488
                system(buf);
489
            }
490
 
491
            //printf("Repository: %s\n", repository.c_str());
492
 
493
            if ( repository[1] == ':' )
494
            {
495
                buf[19] = tolower(repository[0]);
496
                buf[28] = tolower(repository[0]);
497
                system(buf);
498
            }
499
            if ( !install_prefix.empty() )
500
            {
501
                //printf("Install prefix: %s\n", install_prefix.c_str());
502
                if ( install_prefix[1] == ':' )
503
                {
504
                    buf[19] = tolower(install_prefix[0]);
505
                    buf[28] = tolower(install_prefix[0]);
506
                    system(buf);
507
                }
508
            }
509
#endif
510
        } else {
511
            printf("\nUnable to generate build tree, this configuration still contains conflicts.\n");
512
            printf("Either resolve the conflicts or use --ignore-errors\n");
513
        }
514
    } catch (CdlStringException exception) {
515
        exception_handler (exception);
516
    } catch (...) {
517
        exception_handler ();
518
    }
519
 
520
    delete_cdl_data ();
521
    return status;
522
}
523
 
524
// ----------------------------------------------------------------------------
525
bool
526
cdl_exec::cmd_list ()
527
{
528
    bool status = false;
529
    try {
530
        init(false);
531
 
532
        // list the installed packages
533
        std::vector<std::string> packages = pkgdata->get_packages ();
534
        std::sort (packages.begin (), packages.end ());
535
        for (unsigned int package = 0; package < packages.size (); package++) {
536
            const std::vector<std::string> & aliases = pkgdata->get_package_aliases (packages [package]);
537
            printf ("Package %s (%s):\n aliases:", packages [package].c_str (), aliases [0].c_str ());
538
            for (unsigned int alias = 1; alias < aliases.size (); alias++) {
539
                printf (" %s", aliases [alias].c_str ());
540
            }
541
            const std::vector<std::string> & versions = pkgdata->get_package_versions (packages [package]);
542
            printf ("\n versions:");
543
            for (unsigned int version = 0; version < versions.size (); version++) {
544
                printf (" %s", versions [version].c_str ());
545
            }
546
            printf ("\n");
547
        }
548
 
549
        // list the available targets
550
        std::vector<std::string> targets = pkgdata->get_targets ();
551
        std::sort (targets.begin (), targets.end ());
552
        for (unsigned int target = 0; target < targets.size (); target++) {
553
            const std::vector<std::string> & aliases = pkgdata->get_target_aliases (targets [target]);
554
            printf ("Target %s (%s):\n aliases:", targets [target].c_str (), aliases [0].c_str ());
555
            for (unsigned int alias = 1; alias < aliases.size (); alias++) {
556
                printf (" %s", aliases [alias].c_str ());
557
            }
558
            printf ("\n");
559
        }
560
 
561
        // list the available templates
562
        std::vector<std::string> templates = pkgdata->get_templates ();
563
        std::sort (templates.begin (), templates.end ());
564
        for (unsigned int templ = 0; templ < templates.size (); templ++) {
565
            const std::vector<std::string> & versions = pkgdata->get_template_versions (templates [templ]);
566
            printf ("Template %s:\n versions:", templates [templ].c_str ());
567
            for (unsigned int version = 0; version < versions.size (); version++) {
568
                printf (" %s", versions [version].c_str ());
569
            }
570
            printf ("\n");
571
        }
572
 
573
        status = true;
574
    } catch (CdlStringException exception) {
575
        exception_handler (exception);
576
    } catch (...) {
577
        exception_handler ();
578
    }
579
 
580
    delete_cdl_data ();
581
    return status;
582
}
583
 
584
// ----------------------------------------------------------------------------
585
bool
586
cdl_exec::cmd_check ()
587
{
588
    bool status = false;
589
    unsigned int n;
590
 
591
    try {
592
        init(true);
593
        // check() should never invoke the inference engine. The user
594
        // wants to determine the current status, which should not
595
        // change.
596
        // However, updating the savefile is worthwhile because it
597
        // will now contain more accurate information about the state.
598
        // Enabling/disabling debugs is allowed for now because that
599
        // is unlikely to introduce conflicts.
600
        if (debug_level_set) {
601
            this->update_debug_level();
602
        }
603
        if (!no_updates) {
604
            config->save (savefile);
605
        }
606
 
607
        // report current target and template
608
        printf ("Target: %s\n", config->get_hardware ().c_str ());
609
        printf ("Template: %s\n", config->get_template ().c_str ());
610
        std::vector<std::string> template_packages = pkgdata->get_template_packages (config->get_template ());
611
        const std::vector<std::string> & hardware_packages = pkgdata->get_target_packages (config->get_hardware ());
612
        for (n = 0; n < hardware_packages.size (); n++) {
613
            template_packages.push_back (hardware_packages [n]);
614
        }
615
 
616
        // report loaded packages not in the templates
617
        const std::vector<CdlLoadable> & loadables = config->get_loadables ();
618
        std::vector<std::string> added_packages;
619
        std::vector<CdlLoadable>::const_iterator loadable_i;
620
        for (loadable_i = loadables.begin (); loadable_i != loadables.end (); loadable_i++) {
621
            const CdlNode & node = dynamic_cast<CdlNode> (* loadable_i);
622
            if (template_packages.end () == std::find (template_packages.begin (), template_packages.end (), node->get_name ())) {
623
                added_packages.push_back (node->get_name ());
624
            }
625
        }
626
        if (added_packages.size ()) {
627
            printf ("Added:\n");
628
        }
629
        for (n = 0; n < added_packages.size (); n++) {
630
            printf (" %s\n", added_packages [n].c_str ());
631
        }
632
 
633
        // report template packages not in the configuration
634
        std::vector<std::string> removed_packages;
635
        for (n = 0; n < template_packages.size (); n++) {
636
            if (! config->lookup (template_packages [n])) {
637
                removed_packages.push_back (template_packages [n]);
638
            }
639
        }
640
        if (removed_packages.size ()) {
641
            printf ("Removed:\n");
642
        }
643
        for (n = 0; n < removed_packages.size (); n++) {
644
            printf (" %s\n", removed_packages [n].c_str ());
645
        }
646
 
647
        // report packages of non-default version
648
        std::vector<CdlValuable> version_packages;
649
        for (loadable_i = loadables.begin (); loadable_i != loadables.end (); loadable_i++) {
650
            const CdlValuable & valuable = dynamic_cast<CdlValuable> (* loadable_i);
651
            if (pkgdata->get_package_versions (valuable->get_name ()) [0] != valuable->get_value ()) {
652
                version_packages.push_back (valuable);
653
            }
654
        }
655
        if (version_packages.size ()) {
656
            printf ("Version(s):\n");
657
        }
658
        for (n = 0; n < version_packages.size (); n++) {
659
            printf (" %s %s\n", version_packages [n]->get_name ().c_str (), version_packages [n]->get_value ().c_str ());
660
        }
661
 
662
        // report conflicts
663
        const std::list<CdlConflict> & conflicts = config->get_all_conflicts ();
664
        if (conflicts.size ()) {
665
            printf ("%u conflict(s):\n", conflicts.size ());
666
        } else {
667
            printf ("No conflicts\n");
668
        }
669
        report_conflicts();
670
 
671
        status = true;
672
    } catch (CdlStringException exception) {
673
        exception_handler (exception);
674
    } catch (...) {
675
        exception_handler ();
676
    }
677
 
678
    delete_cdl_data ();
679
    return status;
680
}
681
 
682
// ----------------------------------------------------------------------------
683
bool
684
cdl_exec::cmd_resolve ()
685
{
686
    bool status = false;
687
 
688
    try {
689
        init(true);
690
        if (debug_level_set) {
691
            this->update_debug_level();
692
        }
693
        CdlTransactionBody::set_callback_fn(&transaction_callback);
694
        config->resolve_all_conflicts ();
695
        report_conflicts();
696
        if (!no_updates) {
697
            config->save (savefile);
698
        }
699
        if (ignore_errors || (0 == config->get_all_conflicts().size())) {
700
            status = true;
701
        }
702
    } catch (CdlStringException exception) {
703
        exception_handler (exception);
704
    } catch (...) {
705
        exception_handler ();
706
    }
707
 
708
    delete_cdl_data ();
709
    return status;
710
}
711
 
712
// ----------------------------------------------------------------------------
713
// The inference callback. This could give some useful diagnostics, or it
714
// could do useful things when running in some interactive mode. In batch
715
// mode it should not do anything.
716
 
717
CdlInferenceCallbackResult
718
cdl_exec::inference_callback (CdlTransaction transaction)
719
{
720
    return CdlInferenceCallbackResult_Continue;
721
}
722
 
723
// ----------------------------------------------------------------------------
724
// Output a message with indentation after newlines.
725
static void
726
dump_string(unsigned int indent, const std::string& str)
727
{
728
    bool newline_pending = false;
729
    unsigned int i, j;
730
    for (i = 0; i < str.size(); i++) {
731
        if (newline_pending) {
732
            putchar('\n');
733
            if ('\n' != str[i]) {
734
                for (j = 0; j < indent; j++) {
735
                    putchar(' ');
736
                }
737
            }
738
            newline_pending = false;
739
        }
740
        if ('\n' == str[i]) {
741
            newline_pending = true;
742
        } else {
743
            putchar(str[i]);
744
        }
745
    }
746
    if (newline_pending) {
747
        putchar('\n');  // But not the indentation.
748
    }
749
}
750
 
751
// ----------------------------------------------------------------------------
752
// The transaction callback. This should report any changes that have been
753
// made to the configuration. The amount of output depends on the verbosity
754
// level selected by the user.
755
//
756
// 1) quiet     - no output at all
757
// 2) default   - list updates done by the inference engine.
758
// 3) verbose   - this does not currently add anything.
759
// 
760
// There is no reporting of new or resolved conflicts. Resolved
761
// conflicts are probably of no interest in batch mode. New conflicts
762
// will be handled by report_conflicts(). There is also no information
763
// given about active state changes, although arguably there should be
764
// especially in the case of containers.
765
 
766
void
767
cdl_exec::transaction_callback(const CdlTransactionCallback& callback_data)
768
{
769
    if (quiet) {
770
        return;
771
    }
772
 
773
    unsigned int i;
774
    for (i = 0; i < callback_data.value_changes.size(); i++) {
775
        CdlValuable valuable = callback_data.value_changes[i];
776
        if (CdlValueSource_Inferred == valuable->get_source()) {
777
            CdlEvalContext context(0, valuable, 0);
778
            CdlSimpleValue simple_val;
779
            CdlSimpleValue::eval_valuable(context, valuable, simple_val);
780
            std::string msg = std::string("U ") + valuable->get_name() + ", new inferred value ";
781
            std::string value = simple_val.get_value();
782
            if ("" == value) {
783
                msg += "\"\"";
784
            } else {
785
                msg += value;
786
            }
787
            msg += "\n";
788
            dump_string(4, msg);
789
        }
790
    }
791
}
792
 
793
// ----------------------------------------------------------------------------
794
// Report the remaining conflicts in the configuration. These indicate
795
// problems that the user should fix before going further with the
796
// configuration, e.g. before generating a build tree.
797
//
798
// Quiet verbosity level has no effect on this, but at the verbose level
799
// it is a good idea to look for a possible solution to the conflict.
800
 
801
 
802
void
803
cdl_exec::report_conflicts()
804
{
805
    const std::list<CdlConflict>& all_conflicts = config->get_all_conflicts();
806
    std::list<CdlConflict>::const_iterator conf_i;
807
    for (conf_i = all_conflicts.begin(); conf_i != all_conflicts.end(); conf_i++) {
808
        CdlNode     node = (*conf_i)->get_node();
809
 
810
        std::string msg = std::string("C ") + node->get_name() + ", " + (*conf_i)->get_explanation() + "\n";
811
        dump_string(2, msg);
812
 
813
        if (verbose && (*conf_i)->resolution_implemented()) {
814
            // See if there is a possible solution to this conflict.
815
            // This involves creating a transaction, invoking the
816
            // inference engine, and cancelling the transaction
817
            // (thus making sure that nothing actually changes).
818
            //
819
            // NOTE: at some stage libcdl may keep track of solutions
820
            // globally. However, although it will know when a solution
821
            // becomes invalid it will not necessarily try to resolve
822
            // all global conflicts after every change, so attempting
823
            // to do this in a transaction may still be necessary.
824
            CdlTransaction transact = CdlTransactionBody::make(config);
825
            transact->resolve(*conf_i);
826
            if ((*conf_i)->has_known_solution()) {
827
                std::string soln_msg = "  Possible solution:\n";
828
                const std::vector<std::pair<CdlValuable, CdlValue> > & soln = (*conf_i)->get_solution();
829
                unsigned int i;
830
                for (i = 0; i < soln.size(); i++) {
831
                    CdlValuable valuable = soln[i].first;
832
                    soln_msg += valuable->get_name();
833
                    soln_msg += " -> ";
834
                    switch(valuable->get_flavor()) {
835
                      case CdlValueFlavor_Bool :
836
                        if (!soln[i].second.is_enabled()) {
837
                            soln_msg += "0 (disabled)";
838
                        } else {
839
                            soln_msg += "1 (enabled)";
840
                        }
841
                        break;
842
                      case CdlValueFlavor_Data:
843
                        soln_msg += soln[i].second.get_value();
844
                        break;
845
                      case CdlValueFlavor_BoolData:
846
                        if (!soln[i].second.is_enabled()) {
847
                            soln_msg += "0 " + soln[i].second.get_value();
848
                        } else {
849
                            soln_msg += "1 " + soln[i].second.get_value();
850
                        }
851
                        break;
852
                        // An option with flavor none cannot be involved
853
                        // in a solution.
854
                      default:
855
                        soln_msg += "<internal error>";
856
                        break;
857
                    }
858
                    soln_msg += "\n";
859
                }
860
 
861
#if 0
862
                // FIXME: currently this member only works for nested sub-transactions.
863
                if (transact->user_confirmation_required()) {
864
                    msg += "This change affects previous user settings.\n";
865
                }
866
#endif                
867
                dump_string(4, soln_msg);
868
            }
869
            transact->cancel();
870
            delete transact;
871
        }
872
    }
873
}
874
 
875
// ----------------------------------------------------------------------------
876
void
877
cdl_exec::diagnostic_handler (std::string message)
878
{
879
    printf ("%s\n", message.c_str ());
880
}
881
 
882
void cdl_exec::exception_handler (CdlStringException exception) {
883
    printf ("%s\n", exception.get_message ().c_str ());
884
}
885
 
886
void
887
cdl_exec::exception_handler ()
888
{
889
    printf ("Unknown error\n");
890
}
891
 
892
 
893
// ----------------------------------------------------------------------------
894
std::string
895
cdl_exec::resolve_package_alias (const std::string alias)
896
{
897
    std::string package = alias;
898
 
899
    if (! pkgdata->is_known_package (alias)) { // if the alias is not a package name
900
        const std::vector<std::string> & packages = pkgdata->get_packages (); // get packages
901
        for (unsigned int n = 0; n < packages.size (); n++) { // for each package
902
            const std::vector<std::string> & aliases = pkgdata->get_package_aliases (packages [n]); // get package aliases
903
            if (aliases.end () != std::find (aliases.begin (), aliases.end (), alias)) { // if alias is found
904
                package = packages [n]; // note the package
905
                break;
906
            }
907
        }
908
    }
909
    return package;
910
}
911
 
912
std::string
913
cdl_exec::resolve_hardware_alias (const std::string alias)
914
{
915
    std::string target = alias;
916
 
917
    if (! pkgdata->is_known_target (alias)) { // if the alias is not a target name
918
        const std::vector<std::string> & targets = pkgdata->get_targets (); // get targets
919
        for (unsigned int n = 0; n < targets.size (); n++) { // for each target
920
            const std::vector<std::string> & aliases = pkgdata->get_target_aliases (targets [n]); // get target aliases
921
            if (aliases.end () != std::find (aliases.begin (), aliases.end (), alias)) { // if alias is found
922
                target = targets [n]; // note the target
923
                break;
924
            }
925
        }
926
    }
927
    return target;
928
}
929
 
930
// ----------------------------------------------------------------------------
931
// Enable or disable debugging in a configuration.
932
void
933
cdl_exec::update_debug_level()
934
{
935
    CdlNode node = config->lookup("CYGPKG_INFRA_DEBUG");
936
    CdlValuable valuable = 0;
937
    if (0 != node) {
938
        valuable = dynamic_cast<CdlValuable>(node);
939
    }
940
    if (0 == valuable) {
941
        throw CdlStringException("Cannot enable or disable debugging, the infrastructure package is absent");
942
    }
943
 
944
    if (debug_level > 0) {
945
        valuable->enable(CdlValueSource_User);
946
    } else {
947
        valuable->disable(CdlValueSource_User);
948
    }
949
}

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.