source: CMT/HEAD/source/cmt_parser.cxx @ 366

Last change on this file since 366 was 366, checked in by arnault, 17 years ago

Cosmetic: debug messages

  • Property svn:eol-style set to native
File size: 189.2 KB
Line 
1//-----------------------------------------------------------
2// Copyright Christian Arnault LAL-Orsay CNRS
3// arnault@lal.in2p3.fr
4// Modified by garonne@lal.in2p3.fr
5// See the complete license in cmt_license.txt "http://www.cecill.info".
6//-----------------------------------------------------------
7
8#include <stdio.h>
9#include <stdlib.h>
10#include <string.h>
11#include <ctype.h>
12
13//----------------------------------------------------------
14
15#include "cmt_parser.h"
16#include "cmt_version.h"
17
18#include "cmt_database.h"
19#include "cmt_include.h"
20#include "cmt_script.h"
21#include "cmt_generator.h"
22#include "cmt_system.h"
23#include "cmt.h"
24#include "cmt_error.h"
25#include "cmt_cvs.h"
26#include "cmt_lock.h"
27#include "cmt_triggers.h"
28#include "cmt_model.h"
29#include "cmt_awk.h"
30#include "cmt_syntax.h"
31#include "cmt_install_area.h"
32#include "cmt_cmtpath_pattern.h"
33#include "cmt_sequence.h"
34#include "cmt_map.h"
35#include "cmt_project.h"
36#include "cmt_log.h"
37#include "cmt_commands.h"
38
39//----------------------------------------------------------
40//
41//  Static object definitions for the CmtContext class.
42//
43
44static CmtContext Me;
45
46CmtContext::CmtContext ()
47{
48  clear ();
49}
50
51CmtContext::~CmtContext ()
52{
53}
54
55void CmtContext::clear ()
56{
57  m_action         = action_none;
58  m_build_nmake    = false;
59  m_cmt_config     = "";
60  //m_cmt_path.clear ();
61  //m_cmt_path_pwds.clear ();
62  //m_cmt_path_sources.clear ();
63  m_cmt_root       = "";
64  m_cmt_version    = "";
65  m_current_dir     = "";
66  m_current_package = "";
67  m_current_config  = "";
68  m_current_path    = "";
69  m_current_prefix  = "";
70  m_current_cmtpath = "";
71  m_current_offset  = "";
72
73  m_current_access   = DeveloperMode;
74
75  m_current_tag      = "";
76  m_current_target   = "";
77  m_current_version  = "";
78  m_default_path     = "";
79  m_quiet            = false;
80  m_disable_warnings = false;
81  m_warnings         = false;
82  m_recursive        = false;
83
84  m_scope_filtering_mode = default_filtering_mode;
85  m_simulation       = false;
86
87  m_standard_macros_done = false;
88  m_current_access = UserMode;
89  m_current_style = cmt_style;
90  m_current_structuring_style = default_structuring_style;
91  m_all_sets_done = false;
92  m_autoconfigure_cmtpath = false;
93  m_debug = false;
94  if (getenv ("CMTDEBUG") != 0) m_debug = true;
95}
96
97//----------------------------------------------------------
98
99
100//----------------------------------------------------------
101//
102//   Utility classes
103//
104//----------------------------------------------------------
105
106/**
107 *  This PathScanner actor simply displays the package name/version/path
108 *  It is used by the cmt show packages operation
109 */
110class PackageViewer : public PathScanner::actor
111{
112public:
113  void run (const cmt_string& package,
114            const cmt_string& version,
115            const cmt_string& path,
116            const bool without_version_directory=false);
117};
118
119
120/**
121 *  This PathScanner actor accumulates all found packages into a cmt_string_vector
122 *  It is used by the broadcast operation
123 */
124class PackageSelector : public PathScanner::actor
125{
126public:
127  PackageSelector (CmtSystem::cmt_string_vector& uses);
128  void run (const cmt_string& package,
129            const cmt_string& version,
130            const cmt_string& path,
131            const bool without_version_directory=false);
132private:
133  CmtSystem::cmt_string_vector& m_uses;
134};
135
136
137
138/**
139 *  This PathScanner actor collects all packages clients of the specified one
140 *  It is used by the cmt show clients operation
141 */
142class ClientCollector : public PathScanner::actor
143{
144public:
145  ClientCollector (const cmt_string& package,
146                   const cmt_string& version);
147  void run (const cmt_string& package,
148            const cmt_string& version,
149            const cmt_string& path,
150            const bool without_version_directory=false);
151  int count ();
152
153private:
154  const cmt_string& m_package;
155  const cmt_string& m_version;
156  int m_count;
157};
158
159//----------------------------------------------------------
160void PackageViewer::run (const cmt_string& package,
161                         const cmt_string& version,
162                         const cmt_string& path,
163                         const bool without_version_directory)
164{
165  cout << package << " " << version << " " << path << endl;
166}
167
168//----------------------------------------------------------
169PackageSelector::PackageSelector (CmtSystem::cmt_string_vector& uses) : m_uses(uses)
170{
171}
172
173//----------------------------------------------------------
174void PackageSelector::run (const cmt_string& package,
175                           const cmt_string& version,
176                           const cmt_string& path,
177                           const bool without_version_directory)
178{
179  //
180  // this might be called on a package with no version directory.
181  // then simply the version argument is empty.
182  //
183
184  cmt_string r = CmtSystem::file_separator ();
185  r += "requirements";
186
187  cmt_string temp;
188
189  if (version == "")
190    {
191      temp = path;
192      //temp += CmtSystem::file_separator ();
193      //temp += package;
194      temp += CmtSystem::file_separator ();
195      temp += "cmt";
196      temp += r;
197     
198      if (!CmtSystem::test_file (temp)) return;
199    }
200  else
201    {
202      temp = path;
203      //temp += CmtSystem::file_separator ();
204      //temp += package;
205      temp += CmtSystem::file_separator ();
206      temp += version;
207      temp += CmtSystem::file_separator ();
208      temp += "cmt";
209      temp += r;
210     
211      if (!CmtSystem::test_file (temp))
212        {
213          temp = path;
214          //temp += CmtSystem::file_separator ();
215          //temp += package;
216          temp += CmtSystem::file_separator ();
217          temp += version;
218          temp += CmtSystem::file_separator ();
219          temp += "mgr";
220          temp += r;
221         
222          if (!CmtSystem::test_file (temp))
223            {
224              return;
225            }
226        }
227    }
228
229  temp.replace (r.c_str(), "");
230  cmt_string& use = m_uses.add ();
231  use = temp;
232}
233
234//----------------------------------------------------------
235ClientCollector::ClientCollector (const cmt_string& package,
236                                  const cmt_string& version) :
237  m_package (package), m_version (version), m_count (0)
238{
239}
240
241//----------------------------------------------------------
242void ClientCollector::run (const cmt_string& package,
243                           const cmt_string& version,
244                           const cmt_string& path,
245                           const bool without_version_directory)
246{
247  cmt_string dir = path;
248  dir += CmtSystem::file_separator ();
249  dir += package;
250  dir += CmtSystem::file_separator ();     
251  if (version != "" && ! without_version_directory)
252    {
253      dir += version;
254      dir += CmtSystem::file_separator ();
255    }
256
257  cmt_string req;
258 
259  req  = dir;
260  req += "cmt";
261  req += CmtSystem::file_separator ();
262  req += "requirements";
263
264  cmt_string requirements;
265  cmt_string line;
266  CmtSystem::cmt_string_vector words;
267
268  if (CmtSystem::test_file (req))
269    {
270      requirements.read (req);
271    }
272  else
273    {
274      req = dir;
275      req += "mgr";
276      req += CmtSystem::file_separator ();
277      req += "requirements";
278      if (CmtSystem::test_file (req))
279        {
280          requirements.read (req);
281        }
282    }
283
284  if (requirements != "")
285    {
286      int pos = 0;
287      int max_pos = requirements.size ();
288
289      while (pos < max_pos)
290        {
291          int cr = requirements.find (pos, "\r\n");
292          int nl = requirements.find (pos, '\n');
293          int first = nl;
294          int length = 1;
295               
296          if (cr != cmt_string::npos)
297            {
298              if (nl == cmt_string::npos)
299                {
300                  first = cr;
301                  length = 2;
302                }
303              else
304                {
305                  first = (nl < cr) ? nl : cr;
306                  length = (nl < cr) ? 1 : 2;
307                }
308            }
309               
310          if (first == cmt_string::npos)
311            {
312              requirements.substr (pos, line);
313              pos = max_pos;
314            }
315          else if (first > pos)
316            {
317              requirements.substr (pos, first - pos, line);
318              pos = first + length;
319            }
320          else
321            {
322              line.erase (0);
323              pos += length;
324            }
325
326          CmtSystem::split (line, " \t", words);
327
328          if ((words.size () >= 2) && (words[0] == "use")) 
329            {
330              if ((words[1] == m_package) && 
331                  ( (m_version == "") || (words[2] == m_version)))
332                {
333                  cout << "# " << package << " " << version << " " << path;
334                  if (m_version == "" && words.size () > 2)
335                    {
336                      cout << " (use version " << words[2] << ")";
337                    }
338                  cout << endl;
339                  m_count++;
340                }
341            }
342        }
343    }
344}
345
346//----------------------------------------------------------
347int ClientCollector::count ()
348{
349  return (m_count);
350}
351
352
353
354
355//----------------------------------------------------------
356//
357//   The Cmt methods
358//
359//----------------------------------------------------------
360
361
362
363/**
364 *   Append "CONFIG" to the prefix
365 */
366void Cmt::build_config (const cmt_string& prefix,
367                        cmt_string& config)
368{
369  /*
370    Building the config from <prefix>
371  */
372
373  config = prefix;
374  config += "CONFIG";
375}
376
377//----------------------------------------------------------
378void Cmt::build_makefile (const cmt_string& target)
379{
380  Constituent* constituent = 0;
381
382  if (target.size () > 0)
383    {
384      /*
385        Do genmake for one specific target.
386      */
387      constituent = Constituent::find (target);
388      if (constituent != 0)
389        {
390          constituent->build_makefile (Me.m_simulation);
391        }
392    }
393  else
394    {
395      /*
396        Do genmake for all possible targets.
397      */
398      Constituent::build_all_makefiles (Me.m_simulation);
399    }
400}
401
402//----------------------------------------------------------
403void Cmt::build_msdev_file (const cmt_string& target)
404{
405  Constituent* constituent = 0;
406
407  set_standard_macros ();
408
409  if (target != "")
410    {
411      /*
412        Do genmsdev for one specific target.
413      */
414      constituent = Constituent::find (target);
415      if (constituent != 0)
416        {
417          constituent->build_msdev_file (Me.m_simulation);
418        }
419    }
420  else
421    {
422      /*
423        Do genmsdev for all possible targets.
424      */
425      Constituent::build_all_msdev_files (Me.m_simulation);
426    }
427}
428
429/**
430   Visual Studio.net Support                                 
431*/
432void Cmt::build_vsnet_file (const cmt_string& target)       
433{                                                           
434  Constituent* constituent = 0;                             
435                                                             
436  set_standard_macros ();                                   
437                                                             
438  if (target != "")                                         
439    {                                                       
440      /*                                                     
441        Do genvsnet for one specific target.                 
442      */                                                     
443      constituent = Constituent::find (target);             
444      if (constituent != 0)                                 
445        {                                                   
446          constituent->build_vsnet_file (Me.m_simulation);       
447        }                                                   
448    }                                                       
449  else                                                       
450    {                                                       
451      /*                                                     
452        Do genvsnet for all possible targets.               
453      */                                                     
454      Constituent::build_all_vsnet_files (Me.m_simulation);       
455    }                                                       
456}                                                           
457
458//----------------------------------------------------------
459bool Cmt::build_nmake ()
460{
461  return (Me.m_build_nmake);
462}
463
464//----------------------------------------------------------
465void Cmt::build_OS9_makefile (const cmt_string& target)
466{
467  build_makefile (target);
468}
469
470/**
471 *   Convert a package name to its upper case copy
472 */
473void Cmt::build_prefix (const cmt_string& package, cmt_string& prefix)
474{
475  int pos;
476  char c;
477
478  /*
479    Building the prefix from <package>
480  */
481
482  prefix = package;
483
484  for (pos = 0; pos < package.size (); pos++)
485    {
486      c = package[pos];
487      prefix[pos] = toupper (c);
488    }
489}
490
491//----------------------------------------------------------
492void Cmt::clear ()
493{
494  Me.clear ();
495
496  Database::clear ();
497  Include::clear_all ();
498  Script::clear_all ();
499  CmtError::clear ();
500}
501
502//----------------------------------------------------------
503void Cmt::configure ()
504{
505  Log;
506  static bool configured = false;
507
508  if (configured) return;
509
510  Me.clear ();
511
512  log << "configure_default_path" << log_endl;
513  configure_default_path ();
514  log << "configure_version_tag" << log_endl;
515  configure_version_tag ();
516  log << "configure_uname_tag" << log_endl;
517  configure_uname_tag ();
518  log << "configure_hosttype_tag" << log_endl;
519  configure_hosttype_tag ();
520  log << "configure_config_tag" << log_endl;
521  configure_config_tag ();
522  log << "configure_site_tag" << log_endl;
523  configure_site_tag (0);
524  log << "configure_home" << log_endl;
525  // CMTHOME, CMTUSERCONTEXT and CMTPATH
526  configure_home (0);
527  log << "configure_current_dir" << log_endl;
528
529
530  Me.m_autoconfigure_cmtpath = true;
531  configure_cmt_path (0);
532  Me.m_autoconfigure_cmtpath = false;
533
534
535  configure_current_dir ();
536
537  log << "configure_current_package" << log_endl;
538  configure_current_package ();
539  log << "configure_current_structuring_style" << log_endl;
540  configure_current_structuring_style ();
541
542  Use& use = Use::current();
543
544  use.set (Me.m_current_package,
545           Me.m_current_version,
546           Me.m_current_path,
547           "",
548           "");
549
550  use.style = Me.m_current_style;
551
552  use.change_path (Me.m_current_path);
553
554  guess_current_project ();
555
556  if (CmtError::has_pending_error ()) 
557    {
558      Me.m_configure_error = CmtError::get_last_error ();
559    }
560}
561
562//----------------------------------------------------------
563void Cmt::configure_cmt_path (Use* use)
564{
565  if (!Me.m_autoconfigure_cmtpath) return;
566
567  cmt_string s;
568
569  s = Symbol::get_env_value ("CMTPATH");
570
571  {
572    bool q = Me.m_quiet;
573    Me.m_quiet = true; 
574    Symbol::filter_path_value ("CMTPATH", s);
575    Me.m_quiet = q;
576  }
577
578  IProjectFactory& factory = ProjectFactory::instance ();
579  factory.reset ();
580
581  CmtSystem::get_cmt_paths (factory, s, Me.m_cmt_user_context, Me.m_cmt_home);
582}
583
584//----------------------------------------------------------
585void Cmt::configure_config_tag ()
586{
587  Me.m_cmt_config = CmtSystem::get_cmt_config ();
588  if (Me.m_cmt_config != "")
589    {
590      Tag* tag;
591
592      tag = Tag::add (Me.m_cmt_config, PriorityConfig, "CMTCONFIG", 0);
593      tag->mark ();
594    }
595}
596
597//----------------------------------------------------------
598void Cmt::configure_current_cmtpath ()
599{
600  Use& current_use = Use::current ();
601
602  Me.m_current_cmtpath = "";
603  Me.m_current_offset = "";
604
605  Me.m_current_cmtpath = Project::find_in_cmt_paths (current_use.path);
606
607  if (Me.m_current_cmtpath != "")
608    {
609      static const cmt_string empty_string;
610      static const cmt_string fs = CmtSystem::file_separator ();
611
612      Me.m_current_offset = current_use.path;
613
614      /**
615         try to remove this current CMTPATH entry from path.  This
616         has a meaning when the specified path already contains an
617         absolute path.
618      */
619     
620      Me.m_current_offset.replace (Me.m_current_cmtpath, empty_string);
621      if (Me.m_current_offset[0] == CmtSystem::file_separator ())
622        {
623          // Just in case there is a part left after removing the cmtpath entry
624         
625          Me.m_current_offset.replace (fs, empty_string);
626        }
627    }
628}
629
630class CmtMountFilterParser : public FAwk
631{
632public:
633
634  CmtMountFilterParser ()
635  {
636    reset ();
637  }
638
639  void reset ()
640  {
641    m_current_dir = CmtSystem::pwd ();
642    m_done = false;
643    m_prefix = "";
644  }
645
646  bool is_done () const
647  {
648    return (m_done);
649  }
650
651  const cmt_string& get_current_dir () const
652  {
653    return (m_current_dir);
654  }
655
656  void set_prefix (const cmt_string& prefix)
657  {
658    m_prefix = prefix;
659  }
660
661  void filter (const cmt_string& line)
662  {
663    //cout << "line=" << line << endl;
664
665    if (m_done) 
666      {
667        stop ();
668        return;
669      }
670
671    CmtSystem::cmt_string_vector words;
672
673    CmtSystem::split (line, " \t", words);
674
675    int requested = 2;
676
677    if (m_prefix != "")
678      {
679        requested++;
680      }
681
682    if (words.size () < requested) return;
683
684    int n = 0;
685
686    if (m_prefix != "")
687      {
688        if (words[n] != m_prefix) return;
689        n++;
690      }
691
692    cmt_string& path_name = words[n];
693    cmt_string& replacement = words[n+1];
694   
695    if (m_current_dir.find (path_name) != cmt_string::npos)
696      {
697        m_current_dir.replace (path_name, replacement);
698        m_done = true;
699        stop ();
700      }
701  }
702
703private:
704  bool m_done;
705  cmt_string m_prefix;
706  cmt_string m_current_dir;
707};
708
709//----------------------------------------------------------
710void Cmt::configure_current_dir ()
711{
712  cmt_string file_name;
713
714  /*
715    Building current_dir :
716
717    o we first get the physical value (using getwd)
718    o then this value is possibly filtered using the
719    cmt_mount_filter file.
720  */
721
722  CmtMountFilterParser mount_filter;
723
724  /**
725     First try with ${CMTROOT}/mgr/cmt_mount_filter
726     with no prefix on lines
727  */
728
729  file_name = Me.m_default_path;
730  if (file_name != "")
731    {
732      file_name += CmtSystem::file_separator ();
733      file_name += "CMT";
734      file_name += CmtSystem::file_separator ();
735      file_name += Me.m_cmt_version;
736      file_name += CmtSystem::file_separator ();
737      file_name += "mgr";
738      file_name += CmtSystem::file_separator ();
739    }
740
741  file_name += "cmt_mount_filter";
742
743  mount_filter.run (file_name);
744
745  /**
746     Now try with .cmtrc
747     with "mount_filter" keyword
748  */
749
750  mount_filter.set_prefix ("mount_filter");
751
752  mount_filter.run (".cmtrc");
753
754  /**
755     Now try with ${HOME}/.cmtrc
756     with "mount_filter" keyword
757  */
758
759  if (CmtSystem::get_home_directory (file_name))
760    {
761      file_name += CmtSystem::file_separator ();
762      file_name += ".cmtrc";
763      mount_filter.run (file_name);
764    }
765
766  Me.m_current_dir = mount_filter.get_current_dir ();
767}
768
769//----------------------------------------------------------
770void Cmt::configure_current_package ()
771{
772  /*
773    Build current_package and current_prefix.
774
775    This is only possible if we are within the cmt/mgr branch of a
776    standard directory tree (i.e. <package>/<version>/cmt or mgr)
777  */
778
779  cmt_string req = "..";
780  req += CmtSystem::file_separator ();
781  req += "cmt";
782  req += CmtSystem::file_separator ();
783  req += "requirements";
784
785  if (CmtSystem::test_file (req))
786    {
787      Me.m_current_style = cmt_style;
788    }
789  else
790    {
791      cmt_string req = "..";
792      req += CmtSystem::file_separator ();
793      req += "mgr";
794      req += CmtSystem::file_separator ();
795      req += "requirements";
796
797      if (CmtSystem::test_file (req))
798        {
799          Me.m_current_style = mgr_style;
800        }
801      else
802        {
803          // This package is probably a standalone one
804          Me.m_current_style = none_style;
805        }
806    }
807
808
809  if (Me.m_current_style != none_style)
810    {
811      //
812      //  Here there is a ../cmt or ../mgr branch in front of us
813      //  and there is a requirements file there
814      //
815
816      cmt_string up_dir;
817      cmt_string up_branch;
818
819      CmtSystem::dirname (Me.m_current_dir, up_dir);
820      CmtSystem::basename (up_dir, up_branch);
821
822      cmt_string version_file = "..";
823      version_file += CmtSystem::file_separator ();
824      version_file += "cmt";
825      version_file += CmtSystem::file_separator ();
826      version_file += "version.cmt";
827
828      if (CmtSystem::test_file (version_file))
829        {
830          //
831          // There is an explicit version descriptor. This one takes precedence
832          // and forces the structuring style to no directory
833          //
834
835          Me.m_current_package = up_branch;
836          CmtSystem::dirname (up_dir, Me.m_current_path);
837
838          if (Me.m_current_version.read (version_file))
839            {
840              int pos;
841
842              pos = Me.m_current_version.find ('\n');
843              if (pos != cmt_string::npos) Me.m_current_version.erase (pos);
844              pos = Me.m_current_version.find ('\r');
845              if (pos != cmt_string::npos) Me.m_current_version.erase (pos);
846            }
847          else
848            {
849              Me.m_current_version = "v*";
850            }
851
852          if (Me.m_debug)
853            {
854              cout << "Cmt::configure_current_package>" << endl
855                   << " m_current_package " << Me.m_current_package << endl
856                   << " m_current_version " << Me.m_current_version << endl
857                   << " m_current_dir " << Me.m_current_dir << endl
858                   << " pwd " << CmtSystem::pwd ()
859                   << endl;
860            }
861
862          Me.m_current_style = no_version_style;
863        }
864      else if (CmtSystem::is_version_directory (up_branch))
865        {
866          // The up branch IS a version directory.
867
868          Me.m_current_version = up_branch;
869          CmtSystem::dirname (up_dir, up_dir);
870          CmtSystem::basename (up_dir, Me.m_current_package);
871          CmtSystem::dirname (up_dir, Me.m_current_path);
872        }
873      else
874        {
875          // No version descriptor
876          // No version directory. The version is defaulted to v*
877 
878          CmtSystem::basename (up_dir, Me.m_current_package);
879          Me.m_current_version = "v*";
880          CmtSystem::dirname (up_dir, Me.m_current_path);
881
882          Me.m_current_style = no_version_style;
883        }
884
885      build_prefix (Me.m_current_package, Me.m_current_prefix);
886      build_config (Me.m_current_prefix, Me.m_current_config);
887    }
888  else
889    {
890      Me.m_current_package = "cmt_standalone";
891      Me.m_current_version = "";
892      Me.m_current_path = Me.m_current_dir;
893      build_prefix (Me.m_current_package, Me.m_current_prefix);
894      build_config (Me.m_current_prefix, Me.m_current_config);
895      Me.m_current_style = none_style;
896    }
897
898  //cout << "configure_current_package> current style=" << Me.m_current_style << endl;
899}
900
901//----------------------------------------------------------
902void Cmt::configure_current_structuring_style ()
903{
904  cmt_string s;
905
906  s = CmtSystem::getenv ("CMTSTRUCTURINGSTYLE");
907  if (s == "without_version_directory")
908    {
909      Me.m_current_structuring_style = without_version_directory;
910    }
911  else if (s == "with_version_directory")
912    {
913      Me.m_current_structuring_style = with_version_directory;
914    } 
915}
916
917//----------------------------------------------------------
918void Cmt::configure_default_path ()
919{
920  Me.m_default_path = CmtSystem::get_cmt_root ();
921  CmtSystem::get_cmt_version (Me.m_cmt_version);
922  Me.m_cmt_root = Me.m_default_path;
923  Me.m_cmt_root += CmtSystem::file_separator ();
924  Me.m_cmt_root += "CMT";
925  Me.m_cmt_root += CmtSystem::file_separator ();
926  Me.m_cmt_root += Me.m_cmt_version;
927}
928
929//----------------------------------------------------------
930void Cmt::configure_home (Use* use)
931{
932  Me.m_cmt_home = "";
933
934  Symbol* symbol = Symbol::find ("CMTHOME");
935  if (symbol != 0)
936    {
937      Me.m_cmt_home = symbol->build_macro_value ();
938      Symbol::expand (Me.m_cmt_home);
939    }
940  else if (CmtSystem::testenv ("CMTHOME"))
941    {
942      Me.m_cmt_home = CmtSystem::getenv ("CMTHOME");
943    }
944
945  if ((Me.m_cmt_home != "") && !CmtSystem::test_directory (Me.m_cmt_home))
946    {
947      Me.m_cmt_home = "";
948    }
949
950  configure_user_context (0);
951}
952
953//----------------------------------------------------------
954void Cmt::configure_user_context (Use* use)
955{
956  Me.m_cmt_user_context = "";
957
958  Symbol* symbol = Symbol::find ("CMTUSERCONTEXT");
959  if (symbol != 0)
960    {
961      Me.m_cmt_user_context = symbol->build_macro_value ();
962      Symbol::expand (Me.m_cmt_user_context);
963    }
964  else if (CmtSystem::testenv ("CMTUSERCONTEXT"))
965    {
966      Me.m_cmt_user_context = CmtSystem::getenv ("CMTUSERCONTEXT");
967    }
968
969  if ((Me.m_cmt_user_context != "") && !CmtSystem::test_directory (Me.m_cmt_user_context))
970    {
971      Me.m_cmt_user_context = "";
972    }
973
974  if (Me.m_debug) cout << "configure_user_context> user_context=" << Me.m_cmt_user_context << endl;
975
976  configure_cmt_path (0);
977}
978
979//----------------------------------------------------------
980void Cmt::configure_hosttype_tag ()
981{
982  cmt_string hosttype;
983
984  CmtSystem::get_hosttype (hosttype);
985
986  if (hosttype != "")
987    {
988      Tag* tag;
989
990      tag = Tag::add (hosttype, PriorityUname, "HOSTTYPE", 0);
991      tag->mark ();
992    }
993}
994
995//----------------------------------------------------------
996void Cmt::configure_site_tag (Use* use)
997{
998  Symbol* symbol = Symbol::find ("CMTSITE");
999  if (symbol != 0)
1000    {
1001      Me.m_cmt_site = symbol->build_macro_value ();
1002      Symbol::expand (Me.m_cmt_site);
1003    }
1004  else
1005    {
1006      Me.m_cmt_site = CmtSystem::get_cmt_site ();
1007    }
1008
1009  if (Me.m_cmt_site != "")
1010    {
1011      cmt_string s = "CMTSITE";
1012
1013      if (use != 0)
1014        {
1015          s += " in ";
1016        }
1017
1018      Tag* tag;
1019
1020      tag = Tag::add (Me.m_cmt_site, PrioritySite, s, use);
1021      tag->mark ();
1022    }
1023}
1024
1025//----------------------------------------------------------
1026void Cmt::restore_all_tags (Use* use)
1027{
1028    //cerr << "restore_all_tags" << endl;
1029
1030  Cmt::configure_tags (use);
1031
1032    /*
1033      Then get existing extra tags
1034     */
1035
1036  if (CmtSystem::testenv ("CMTEXTRATAGS"))
1037    {
1038      cmt_string s = "CMTEXTRATAGS";
1039
1040      if (use != 0)
1041        {
1042          s += " in ";
1043        }
1044
1045      Tag* tag;
1046      CmtSystem::cmt_string_vector words;
1047     
1048      cmt_string tags = CmtSystem::getenv ("CMTEXTRATAGS");
1049     
1050      CmtSystem::split (tags, " \t,", words);
1051
1052      Me.m_extra_tags = ",";
1053     
1054      for (int i = 0; i < words.size (); i++)
1055        {
1056          const cmt_string& a = words[i];
1057
1058          Me.m_extra_tags += a;
1059          Me.m_extra_tags += ",";
1060         
1061          tag = Tag::add (a, PriorityUserTag, s, use);
1062         
1063          tag->mark ();
1064        }
1065    }
1066}
1067
1068//----------------------------------------------------------
1069void Cmt::configure_tags (Use* use)
1070{
1071  cmt_string config_tag;
1072
1073  Log;
1074
1075  //if (Me.m_debug) cout << "configure_tags0> current_tag=" << Me.m_current_tag << endl;
1076
1077  log << "current_tag=" << Me.m_current_tag << log_endl;
1078
1079  Symbol* symbol = Symbol::find ("CMTCONFIG");
1080  if (symbol != 0)
1081    {
1082      bool show_set_hidden = false;
1083
1084      if (Me.m_action == action_show_set)
1085        {
1086          show_set_hidden = true;
1087          Me.m_action = action_none;
1088        }
1089
1090      config_tag = symbol->build_macro_value ();
1091      Symbol::expand (config_tag);
1092
1093      if (show_set_hidden)
1094        {
1095          show_set_hidden = false;
1096          Me.m_action = action_show_set;
1097        }
1098    }
1099  else if (CmtSystem::testenv ("CMTCONFIG"))
1100    {
1101      config_tag = CmtSystem::getenv ("CMTCONFIG");
1102    }
1103  else if (CmtSystem::testenv ("CMTBIN"))
1104    {
1105      config_tag = CmtSystem::getenv ("CMTBIN");
1106    }
1107
1108  if (config_tag == "")
1109    {
1110      CmtSystem::get_uname (config_tag);
1111    }
1112
1113  //if (Me.m_debug) cout << "configure_tags> current_tag=" << Me.m_current_tag << endl;
1114  log << "current_tag=" << Me.m_current_tag << log_endl;
1115
1116  cmt_string s = "CMTCONFIG";
1117
1118  if (use != 0)
1119    {
1120      s += " in ";
1121    }
1122
1123  Tag* tag;
1124
1125  tag = Tag::add (config_tag, PriorityConfig, s, use);
1126  tag->mark ();
1127
1128    //Me.m_current_tag = config_tag;
1129}
1130
1131//----------------------------------------------------------
1132void Cmt::configure_uname_tag ()
1133{
1134  cmt_string uname;
1135
1136  CmtSystem::get_uname (uname);
1137
1138  if (uname != "")
1139    {
1140      Tag* tag;
1141
1142      tag = Tag::add (uname, PriorityUname, "uname", 0);
1143      tag->mark ();
1144    }
1145}
1146
1147//----------------------------------------------------------
1148void Cmt::configure_version_tag ()
1149{
1150  int v = 0;
1151  int r = 0;
1152  int p = 0;
1153
1154  CmtSystem::is_version_directory (CMTVERSION, v, r, p);
1155
1156  Tag* tag;
1157
1158  static char temp[80];
1159
1160  sprintf (temp, "CMTv%d", v);
1161
1162  tag = Tag::add (temp, PriorityVersion, "CMTVERSION", 0);
1163  tag->mark ();
1164
1165  sprintf (temp, "CMTr%d", r);
1166
1167  tag = Tag::add (temp, PriorityVersion, "CMTVERSION", 0);
1168  tag->mark ();
1169
1170  sprintf (temp, "CMTp%d", p);
1171
1172  tag = Tag::add (temp, PriorityVersion, "CMTVERSION", 0);
1173  tag->mark ();
1174
1175}
1176
1177//----------------------------------------------------------
1178//
1179//   Actions
1180//
1181//----------------------------------------------------------
1182
1183class AwkActor : public Awk
1184{
1185public:
1186
1187  void filter (const cmt_string& line)
1188      {
1189        cout << line << endl;
1190      }
1191};
1192
1193//----------------------------------------------------------
1194void Cmt::do_awk (const ArgParser& ap)
1195{
1196  if (ap.arguments.size () < 1)
1197    {
1198      cerr << "#CMT> cmt awk <file> <pattern>" << endl;
1199      return;
1200    }
1201
1202  const cmt_string& file = ap.arguments[0];
1203  const cmt_string& pattern = ap.arguments[1];
1204  cmt_string text;
1205
1206  text.read (file);
1207
1208  static AwkActor a;
1209
1210  cmt_regexp exp (pattern);
1211
1212  a.run (text, exp);
1213}
1214
1215//----------------------------------------------------------
1216void Cmt::do_broadcast (const ArgParser& ap)
1217{
1218  Use::UsePtrVector& Uses = Use::get_ordered_uses ();
1219
1220  CmtSystem::cmt_string_vector uses;
1221  CmtSystem::cmt_string_vector packages;
1222  CmtSystem::cmt_string_vector versions;
1223  CmtSystem::cmt_string_vector path_selections;
1224  CmtSystem::cmt_string_vector selections;
1225  CmtSystem::cmt_string_vector exclusions;
1226  cmt_string begin;
1227  cmt_string command;
1228  bool is_cmt = false;
1229  int first = 0;
1230  int i;
1231  bool ignore_errors = false;
1232  bool all_packages = false;
1233
1234  bool local = true;
1235
1236  for (i = 0; i < ap.arguments.size (); i++)
1237    {
1238      const cmt_string& w = ap.arguments[i];
1239
1240      //cerr << "broadcast: arg=[" << w << "]" << endl;
1241
1242      if (command == "")
1243        {
1244          if (w.substr (0, 13) == "-all_packages")
1245            {
1246              local = false;
1247              all_packages = true;
1248            }
1249          else if (w.substr (0, 7) == "-depth=")
1250            {
1251              local = false;
1252
1253              cmt_string depth_str;
1254              int depth_value = 0;
1255                         
1256              w.substr (7, depth_str);
1257              if ((sscanf (depth_str.c_str (), "%d", &depth_value) < 1) ||
1258                  (depth_value < 1))
1259                {
1260                  // Syntax error
1261                  //  We shall restrict to packages found within
1262                  // the <depth_value> first elements of CMTPATH.
1263                  //  If CMTPATH is empty, nothing is selected.
1264                  // depth=1 is equivalent to local
1265                }
1266
1267              Project::fill_selection (depth_value, path_selections);
1268            }
1269          else if (w.substr (0, 9) == "-exclude=")
1270            {
1271              cmt_string exclusion;
1272
1273              w.substr (9, exclusion);
1274
1275              int size = exclusion.size ();
1276             
1277              if (size >= 2)
1278                {
1279                  if (((exclusion[0] == '"') && (exclusion[size - 1] == '"')) ||
1280                      ((exclusion[0] == '\'') && (exclusion[size - 1] == '\'')))
1281                    {
1282                      exclusion.erase (size - 1);
1283                      exclusion.erase (0, 1);
1284                    }
1285
1286                  CmtSystem::split (exclusion, " \t", exclusions);
1287                }
1288            }
1289          else if (w.substr (0, 7) == "-global")
1290            {
1291              path_selections.clear ();
1292
1293              local = false;
1294            }
1295          else if (w.substr (0, 6) == "-local")
1296            {
1297              local = true;
1298            }
1299          else if (w.substr (0, 8) == "-select=")
1300            {
1301              cmt_string selection;
1302
1303              w.substr (8, selection);
1304
1305              //cerr << "Select=[" << selection << "]" << endl;
1306
1307              int size = selection.size ();
1308             
1309              if (size >= 2)
1310                {
1311                  if (((selection[0] == '"') && (selection[size - 1] == '"')) ||
1312                      ((selection[0] == '\'') && (selection[size - 1] == '\'')))
1313                    {
1314                      selection.erase (size - 1);
1315                      selection.erase (0, 1);
1316                    }
1317                }
1318
1319              CmtSystem::split (selection, " \t", selections);
1320
1321              //cerr << "Selections.size () = " << selections.size () << endl;
1322            }
1323          else if (w.substr (0, 7) == "-begin=")
1324            {
1325              w.substr (7, begin);
1326            }
1327          else
1328            {
1329              command = w;
1330            }
1331        }
1332      else
1333        {
1334          command += " ";
1335          command += w;
1336        }
1337
1338    }
1339
1340  if (local)
1341    {
1342      Project::fill_selection (1, path_selections);
1343    }
1344
1345  if (command[0] == '-')
1346    {
1347      ignore_errors = true;
1348      command.erase (0, 1);
1349    }
1350
1351  //if (command.substr (0, 3) == "cmt") is_cmt = true;
1352
1353  if (all_packages)
1354    {
1355      PackageSelector selector (uses);
1356      PathScanner scanner;
1357      Project::scan_paths (scanner, selector);
1358    }
1359  else
1360    {
1361      for (i = Uses.size () - 1; i >= 0; i--)
1362        {
1363          Use* use = Uses[i];
1364                 
1365          if (use->discarded) continue;
1366          if (use->m_hidden) continue;
1367
1368          if (!use->located ())
1369            {
1370              if (!Me.m_quiet)
1371                {
1372                  cerr << "#CMT> package " << use->get_package_name () <<
1373                      " " << use->version << " " << use->path <<
1374                      " not found" <<
1375                      endl;
1376                }
1377            }
1378          else
1379            {
1380              if (use->get_package_name () != "CMT")
1381                {
1382                  cmt_string& s = uses.add ();
1383
1384                  use->get_full_path (s);
1385
1386                  s += CmtSystem::file_separator ();
1387                  if (use->style == mgr_style) s += "mgr";
1388                  else s += "cmt";
1389
1390                  cmt_string& v = versions.add ();
1391                  v = use->version;
1392
1393                  cmt_string& p = packages.add ();
1394                  p = use->get_package_name ();
1395
1396                  //cout << ">>> adding " << s << " to selection" << endl;
1397                }
1398            }
1399        }
1400         
1401      {
1402        cmt_string& s = uses.add ();
1403                 
1404        Use* use = &(Use::current ());
1405
1406        if (use->get_package_name ().find ("cmt_standalone") != cmt_string::npos)
1407          {
1408            s = CmtSystem::pwd ();
1409          }
1410        else
1411          {
1412            use->get_full_path (s);
1413
1414            s += CmtSystem::file_separator ();
1415                 
1416            if (use->style == mgr_style) s += "mgr";
1417            else s += "cmt";
1418          }
1419
1420        cmt_string& v = versions.add ();
1421        v = use->version;
1422
1423        cmt_string& p = packages.add ();
1424        p = use->get_package_name ();
1425
1426        //cout << ">>> adding current " << s << " to selection" << endl;
1427      }
1428    }
1429
1430  bool started = false;
1431
1432  if (begin == "") started = true;
1433
1434  set_standard_macros ();
1435  Cmt::reset_all_sets_done ();
1436  Symbol::all_set ();
1437
1438  for (i = 0; i < uses.size (); i++)
1439    {
1440      const cmt_string& s = uses[i];
1441      const cmt_string& v = versions[i];
1442      const cmt_string& p = packages[i];
1443      cmt_string cmtpath;
1444
1445      bool ok = true;
1446      bool selected = true;
1447      bool excluded = false;
1448
1449      if (path_selections.size () > 0)
1450        {
1451          selected = false;
1452
1453          for (int j = 0; j < path_selections.size (); j++)
1454            {
1455              const cmt_string& sel = path_selections[j];
1456             
1457              if (s.find (sel) != cmt_string::npos) 
1458                {
1459                  cmtpath = sel;
1460                  selected = true;
1461                  break;
1462                }
1463            }
1464
1465          ok = selected;
1466        }
1467
1468      if (ok)
1469        {
1470          if (selections.size () > 0)
1471            {
1472              selected = false;
1473             
1474              for (int j = 0; j < selections.size (); j++)
1475                {
1476                  const cmt_string& sel = selections[j];
1477                 
1478                  if (s.find (sel) != cmt_string::npos) 
1479                    {
1480                      selected = true;
1481                      break;
1482                    }
1483                }
1484             
1485              ok = selected;
1486            }
1487        }
1488
1489      if (ok && !started)
1490        {
1491          if (s.find (begin) != cmt_string::npos)
1492            {
1493              started = true;
1494              ok = true;
1495            }
1496          else
1497            {
1498              ok = false;
1499            }
1500        }
1501
1502
1503      if (ok)
1504        {
1505          excluded = false;
1506
1507          for (int j = 0; j < exclusions.size (); j++)
1508            {
1509              const cmt_string& exc = exclusions[j];
1510             
1511              if (s.find (exc) != cmt_string::npos) 
1512                {
1513                  excluded = true;
1514                  break;
1515                }
1516            }
1517
1518          if (excluded) ok = false;
1519        }
1520
1521      if (!ok) 
1522        {
1523          continue;
1524        }
1525
1526
1527
1528      if (!CmtSystem::cd (s))
1529        {
1530          if (s.find ("cmt_standalone") != cmt_string::npos)
1531            {
1532              cerr << "#CMT> Currently not in a CMT package" << endl;
1533            }
1534          else
1535            {
1536              cerr << "#CMT> Cannot move to the package in " << s << " (" << i+1 << "/" 
1537                   << uses.size () << ")"<< endl;
1538            }
1539
1540          if (!ignore_errors) break;
1541
1542          continue;
1543        }
1544
1545      if (CmtLock::check () == CmtLock::locked_by_another_user)
1546        {
1547          cerr << "#CMT> Ignore locked package in " << s << " (" << i+1 << "/" 
1548               << uses.size () << ")" << endl;
1549          continue;
1550        }
1551
1552      if (cmtpath == "")
1553        {
1554          cmt_string sel = CmtSystem::pwd ();
1555          cmtpath = Project::find_in_cmt_paths (sel);
1556        }
1557
1558      cmt_string cmd = command;
1559      static const cmt_string version_template = "<version>";
1560      cmd.replace_all (version_template, v);
1561
1562      static const cmt_string package_template = "<package>";
1563      cmd.replace_all (package_template, p);
1564
1565      static const cmt_string cmtpath_template = "<package_cmtpath>";
1566      cmd.replace_all (cmtpath_template, cmtpath);
1567
1568      static const cmt_string offset_template = "<package_offset>";
1569
1570      static const cmt_string empty_string;
1571      static const cmt_string fs = CmtSystem::file_separator ();
1572      cmt_string offset = s;
1573      offset.replace (cmtpath, empty_string);
1574      if (offset[0] == CmtSystem::file_separator ())
1575        {
1576          offset.replace (fs, empty_string);
1577        }
1578      CmtSystem::dirname (offset, offset);
1579
1580      cmt_string n;
1581      CmtSystem::basename (offset, n);
1582      if (n == p)
1583        {
1584          CmtSystem::dirname (offset, offset);
1585        }
1586      else
1587        {
1588          CmtSystem::dirname (offset, offset);
1589          CmtSystem::dirname (offset, offset);
1590        }
1591
1592      cmd.replace_all (offset_template, offset);
1593
1594
1595      cout << "#--------------------------------------------------------------" << endl;
1596      cout << "# Now trying [" << cmd << "] in " << s << " (" << i+1 << "/" << uses.size () 
1597           << ")" << endl;
1598      cout << "#--------------------------------------------------------------" << endl;
1599
1600      if (is_cmt)
1601        {
1602          //
1603          //  There is a bug in the recursive use of the parser. Macros are not set correctly.
1604          //  Thus the recursive optimization is now discarded.
1605          //
1606          if (parser (cmd) != 0)
1607            {
1608              CmtError::set (CmtError::execution_error, cmd);
1609              break;
1610            }
1611        }
1612      else
1613        {
1614          int status = CmtSystem::execute (cmd);
1615
1616          //cerr << "do_broadcast> status=" << status << " ignore_errors=" << ignore_errors << endl;
1617
1618          if ((status != 0) && !ignore_errors)
1619              //if ((status != 0) && !ignore_errors)
1620            {
1621              if (status != 2) CmtError::set (CmtError::execution_error, cmd);
1622              break;
1623            }
1624        }
1625    }
1626}
1627
1628//----------------------------------------------------------
1629void Cmt::do_build_constituent_makefile (const ArgParser& ap)
1630{
1631  if (CmtLock::check () == CmtLock::locked_by_another_user)
1632    {
1633      CmtError::set (CmtError::conflicting_lock, "build_constituent_makefile>");
1634      return;
1635    }
1636  if (ap.arguments.size () > 0) 
1637    {
1638      set_standard_macros ();
1639      Generator::build_constituent_makefile (ap.arguments[0]);
1640    }
1641}
1642
1643//----------------------------------------------------------
1644void Cmt::do_build_constituents_makefile (const ArgParser& ap)
1645{
1646  if (CmtLock::check () == CmtLock::locked_by_another_user)
1647    {
1648      CmtError::set (CmtError::conflicting_lock, "build_constituents_makefile>");
1649      return;
1650    }
1651  set_standard_macros ();
1652
1653  Generator::build_constituents_makefile (Me.m_current_package, ap.arguments);
1654}
1655
1656//----------------------------------------------------------
1657void Cmt::do_build_dependencies (const ArgParser& ap,
1658                                 int argc,
1659                                 char* argv[])
1660{
1661  if (CmtLock::check () == CmtLock::locked_by_another_user)
1662    {
1663      CmtError::set (CmtError::conflicting_lock, "build_dependencies>");
1664      return;
1665    }
1666  if (ap.arguments.size () > 0)
1667    {
1668      set_standard_macros ();
1669
1670      Generator::build_dependencies (ap.arguments);
1671    }
1672}
1673
1674//----------------------------------------------------------
1675void Cmt::do_build_library_links (const ArgParser& ap)
1676{
1677  cmt_string cmtinstallarea = "";
1678  cmt_string tag = "";
1679  cmt_string shlibsuffix;
1680  cmt_string symlinkcmd;
1681
1682  if (CmtLock::check () == CmtLock::locked_by_another_user)
1683    {
1684      CmtError::set (CmtError::conflicting_lock, "build_library_links>");
1685      return;
1686    }
1687
1688  set_standard_macros ();
1689
1690  Use::UsePtrVector& Uses = Use::get_ordered_uses ();
1691  Use& current_use = Use::current ();
1692  int i;
1693
1694  {
1695    Symbol* macro = Symbol::find ("shlibsuffix");
1696    if (macro == 0) return;
1697    shlibsuffix = macro->build_macro_value ();
1698    Symbol::expand (shlibsuffix);
1699  }
1700
1701  {
1702    Symbol* macro = Symbol::find ("library_install_command");
1703    if (macro != 0)
1704      {
1705        symlinkcmd = macro->build_macro_value ();
1706        Symbol::expand (symlinkcmd);
1707      }
1708  }
1709
1710  if (current_use.get_strategy ("InstallArea"))
1711    {
1712      const CmtInstallAreaMgr& ia_mgr = CmtInstallAreaMgr::instance ();
1713
1714      //cout << "#IA2>" << endl;
1715     
1716      cmt_string s1 = ia_mgr.get_installarea ();
1717
1718      {
1719        Symbol* symbol = Symbol::find ("CMTINSTALLAREA");
1720        if (symbol != 0)
1721          {
1722            s1 = symbol->build_macro_value ();
1723            Symbol::expand (s1);
1724          }
1725      }
1726
1727      cmtinstallarea = s1;
1728                 
1729      cmt_string s2;
1730
1731      {
1732        Symbol* macro = Symbol::find ("tag");
1733        if (macro != 0)
1734          {
1735            s2 = macro->build_macro_value ();
1736            Symbol::expand (s2);
1737          }
1738      }
1739
1740      tag = s2;
1741
1742      cmt_string s = s1;
1743      s += CmtSystem::file_separator ();
1744      s += s2;
1745      s += CmtSystem::file_separator ();
1746      s += "lib";
1747
1748      CmtSystem::mkdir (s);
1749    }
1750
1751  current_use.build_library_links (cmtinstallarea, tag, shlibsuffix, symlinkcmd);
1752
1753  for (i = 0; i < Uses.size (); i++)
1754    {
1755      Use* use = Uses[i];
1756
1757      if (use == 0) continue;
1758      if (use->discarded) continue;
1759      if (use->m_hidden) continue;
1760
1761      if (use->get_package_name () == "CMT") continue;
1762      if (use->get_package_name () == current_use.get_package_name ()) continue;
1763
1764      use->build_library_links (cmtinstallarea, tag, shlibsuffix, symlinkcmd);
1765    }
1766}
1767
1768//----------------------------------------------------------
1769void Cmt::do_build_make_setup (const ArgParser& ap)
1770{
1771  if (CmtLock::check () == CmtLock::locked_by_another_user)
1772    {
1773      CmtError::set (CmtError::conflicting_lock, "build_make_setup>");
1774      return;
1775    }
1776  set_standard_macros ();
1777  Generator::build_make_setup (Me.m_current_package);
1778}
1779
1780//----------------------------------------------------------
1781void Cmt::do_build_msdev (const ArgParser& ap)
1782{
1783  if (CmtLock::check () == CmtLock::locked_by_another_user)
1784    {
1785      CmtError::set (CmtError::conflicting_lock, "build_msdev>");
1786      return;
1787    }
1788
1789  if (true)
1790    {
1791      set_standard_macros ();
1792      if (ap.arguments.size () > 0) build_msdev_file (ap.arguments[0]);
1793      else build_msdev_file ("");
1794    }
1795}
1796
1797void Cmt::do_build_CMT_pacman (const ArgParser& ap)
1798{
1799  cmt_string pacman_file;
1800
1801  pacman_file = Me.m_cmt_root;
1802  pacman_file += CmtSystem::file_separator ();
1803  pacman_file += "mgr";
1804  pacman_file += CmtSystem::file_separator ();
1805  pacman_file += "CMT.pacman";
1806
1807  cmt_string pacman;
1808  cmt_string pattern = "<version>";
1809  cmt_string replacement = CMTVERSION;
1810
1811  pacman.read (pacman_file);
1812
1813  pacman.replace_all (pattern, replacement);
1814
1815  cout << pacman << endl;
1816}
1817
1818// Visual Studio.net Support                                                 
1819//----------------------------------------------------------                 
1820void Cmt::do_build_vsnet (const ArgParser& ap)     
1821{                                                                           
1822  if (CmtLock::check () == CmtLock::locked_by_another_user)                 
1823    {                                                                       
1824      CmtError::set (CmtError::conflicting_lock, "build_vsnet>");           
1825      return;                                                               
1826    }                                                                       
1827                                                                             
1828  if (true)                                                                 
1829    {                                                                       
1830      set_standard_macros ();                                               
1831      if (ap.arguments.size () > 0) build_vsnet_file (ap.arguments[0]);           
1832      else build_vsnet_file ("");                                           
1833    }                                                                       
1834}                                                                           
1835
1836//----------------------------------------------------------
1837void Cmt::do_build_os9_makefile (const ArgParser& ap)
1838{
1839  if (CmtLock::check () == CmtLock::locked_by_another_user)
1840    {
1841      CmtError::set (CmtError::conflicting_lock, "build_os9_makefile>");
1842      return;
1843    }
1844
1845  if (ap.arguments.size () > 0) 
1846    {
1847      set_standard_macros ();
1848      build_OS9_makefile (ap.arguments[0]);
1849    }
1850}
1851
1852//----------------------------------------------------------
1853void Cmt::do_build_prototype (const ArgParser& ap)
1854{
1855  if (CmtLock::check () == CmtLock::locked_by_another_user)
1856    {
1857      CmtError::set (CmtError::conflicting_lock, "build_prototype>");
1858      return;
1859    }
1860
1861  if (ap.arguments.size () > 0) 
1862    {
1863      set_standard_macros ();
1864      Generator::build_prototype (ap.arguments[0]);
1865    }
1866}
1867
1868//----------------------------------------------------------
1869void Cmt::do_build_readme (const ArgParser& ap)
1870{
1871  if (CmtLock::check () == CmtLock::locked_by_another_user)
1872    {
1873      CmtError::set (CmtError::conflicting_lock, "build_readme>");
1874      return;
1875    }
1876
1877  set_standard_macros ();
1878  Generator::build_readme (ap.arguments);
1879}
1880
1881//----------------------------------------------------------
1882void Cmt::do_build_tag_makefile (const ArgParser& ap)
1883{
1884  if (CmtLock::check () == CmtLock::locked_by_another_user)
1885    {
1886      CmtError::set (CmtError::conflicting_lock, "build_tag_makefile>");
1887      return;
1888    }
1889
1890  print_macros (Make);
1891}
1892
1893//----------------------------------------------------------
1894void Cmt::do_build_temporary_name (const ArgParser& ap)
1895{
1896  cmt_string name = CmtSystem::get_temporary_name ();
1897  cout << name << endl;
1898}
1899
1900//----------------------------------------------------------
1901void Cmt::do_build_triggers (const ArgParser& ap)
1902{
1903  if (CmtLock::check () == CmtLock::locked_by_another_user)
1904    {
1905      CmtError::set (CmtError::conflicting_lock, "build_tag_makefile>");
1906      return;
1907    }
1908
1909  if (ap.arguments.size () > 0) 
1910    {
1911      set_standard_macros ();
1912      TriggerGenerator::run (ap.arguments[0]);
1913    }
1914}
1915
1916//----------------------------------------------------------
1917void Cmt::do_build_windefs (const ArgParser& ap)
1918{
1919  if (CmtLock::check () == CmtLock::locked_by_another_user)
1920    {
1921      CmtError::set (CmtError::conflicting_lock, "build_windefs>");
1922      return;
1923    }
1924
1925  if (ap.arguments.size () > 0) 
1926    {
1927      set_standard_macros ();
1928      Generator::build_windefs (ap.arguments[0]);
1929    }
1930}
1931
1932//----------------------------------------------------------
1933void Cmt::do_check_configuration (const ArgParser& ap)
1934{
1935  cmt_string env;
1936  Tag* tag;
1937
1938  set_standard_macros ();
1939
1940  static CmtSystem::cmt_string_vector tags;
1941
1942  CmtSystem::split (Me.m_extra_tags, " \t,", tags);
1943
1944  for (int i = 0; i < tags.size (); i++)
1945    {
1946      const cmt_string& t = tags[i];
1947
1948      tag = Tag::find (t);
1949      if (tag == 0) continue;
1950
1951      if (!Tag::check_tag_used (tag) && !Symbol::check_tag_used (tag)) 
1952        {
1953          cerr << "#CMT> The tag " << t << " is not used in any tag expression. Please check spelling" << endl;
1954        }
1955    }
1956
1957  Symbol::check_all_paths ();
1958
1959  env = CmtSystem::getenv ("CMTSITE");
1960  if (env == "") 
1961    {
1962      return;
1963    }
1964
1965  tag = Tag::find (env);
1966  if (tag == 0) 
1967    {
1968      return;
1969    }
1970
1971  if (!Tag::check_tag_used (tag) && !Symbol::check_tag_used (tag) && Cmt::get_warnings ()) 
1972    {
1973      cerr << "#CMT> The CMTSITE value " << env << " is not used in any tag expression. Please check spelling" << endl;
1974    }
1975
1976}
1977
1978//----------------------------------------------------------
1979void Cmt::do_check_files (const ArgParser& ap)
1980{
1981  if (ap.arguments.size () >= 2) 
1982    {
1983      cmt_string first_file = ap.arguments[0];
1984      cmt_string second_file = ap.arguments[1];
1985         
1986      if (first_file == "") return;
1987      if (second_file == "") return;
1988         
1989      CmtSystem::compare_and_update_files (first_file, second_file);
1990    }
1991}
1992
1993//----------------------------------------------------------
1994void Cmt::do_check_version (const ArgParser& ap)
1995{
1996  if (ap.arguments.size () > 0)
1997    {
1998      cmt_string name = ap.arguments[0];
1999         
2000      if (name == "") return;
2001      int v = 0;
2002      int r = 0;
2003      int p = 0;
2004         
2005      bool ok = CmtSystem::is_version_directory (name, v, r, p);
2006         
2007      if (ok)
2008        {
2009          cout << "# " << name << " is version " << v << " release " << r << " patch " << p << endl;
2010        }
2011      else
2012        {
2013          cout << "# " << name << " is not a version tag" << endl;
2014        }
2015    }
2016}
2017
2018//----------------------------------------------------------
2019void Cmt::do_checkout (const ArgParser& ap)
2020{
2021  Cvs::checkout (ap.arguments);
2022}
2023
2024//----------------------------------------------------------
2025void Cmt::do_cleanup (const ArgParser& ap)
2026{
2027  print_clean (ap.mode);
2028}
2029
2030//----------------------------------------------------------
2031void Cmt::do_config (const ArgParser& ap)
2032{
2033  if (CmtLock::check () == CmtLock::locked_by_another_user)
2034    {
2035      CmtError::set (CmtError::conflicting_lock, "config>");
2036      return;
2037    }
2038
2039    //Use::UsePtrVector& Uses = Use::get_ordered_uses ();
2040
2041  Use& current_use = Use::current ();
2042
2043  if (Me.m_debug)
2044    {
2045      cout << "Cmt::do_config> " << endl;
2046      cout << "pwd " << CmtSystem::pwd () << endl;
2047      cout << "current_dir " << Me.m_current_dir << endl;
2048      cout << "default_path " << Me.m_default_path << endl;
2049      cout << "cmt config " <<
2050          Me.m_current_package << " " <<
2051          Me.m_current_version << " " <<
2052          Me.m_current_path << endl;
2053    }
2054
2055  if (Me.m_current_package == "CMT") return;
2056  if (Me.m_current_package == "methods") return;
2057
2058  cmt_string branch;
2059
2060  CmtSystem::basename (Me.m_current_dir, branch);
2061
2062  if ((branch != "mgr") && (branch != "cmt"))
2063    {
2064
2065        //
2066        // Here we are in a standalone package (ie completely unstructured)
2067        //
2068
2069      if (CmtSystem::test_file ("requirements"))
2070        {
2071          cout << "------------------------------------------" << endl;
2072          cout << "Configuring environment for standalone package." << endl;
2073          cout << "CMT version " << Me.m_cmt_version << "." << endl;
2074          cout << "System is " << Me.m_cmt_config << endl;
2075          cout << "------------------------------------------" << endl;
2076
2077          install_test_setup_scripts ();
2078          install_test_cleanup_scripts ();
2079
2080          Generator::build_default_makefile ();
2081        }
2082      else
2083        {
2084          cout << "==============================================" << endl;
2085          cout << "cmt config must be operated either upon "
2086            "an existing package" << endl;
2087          cout << " (ie. when a requirements file already exists)" << endl;
2088          cout << "   > cd ..." << endl;
2089          cout << "   > cmt config" << endl;
2090          cout << "or to create a new package" << endl;
2091          cout << "   > cmt config <package> <version> [<path>]" << endl;
2092          cout << "==============================================" << endl;
2093        }
2094
2095      return;
2096    }
2097
2098  configure_current_package ();
2099
2100  Generator::build_default_makefile ();
2101
2102  CmtSystem::cmt_string_vector makes;
2103  cmt_regexp expression ("[.]n?make(sav)?$");
2104
2105  CmtSystem::scan_dir (".", expression, makes);
2106 
2107  if (makes.size () > 0)
2108    {
2109      cout << "Removing all previous make fragments from " << branch << endl;
2110
2111      for (int i = 0; i < makes.size (); i++)
2112        {
2113          const cmt_string& s = makes[i];
2114          CmtSystem::cmt_string_vector words;
2115          CmtSystem::split (s, '.', words);
2116          if (words.size()>=2)
2117              if (CmtSystem::get_makefile_suffix () == "nmake" && words[1] == "nmake")
2118                      CmtSystem::remove_file (s);
2119              else if (CmtSystem::get_makefile_suffix () == "make" && words[1] == "make")
2120                      CmtSystem::remove_file (s);
2121        }
2122    }
2123 
2124
2125  CmtSystem::cd ("..");
2126
2127  CmtSystem::scan_dir (Me.m_cmt_config, expression, makes); 
2128   
2129  if (makes.size () > 0) 
2130    {
2131      cout << "Removing all previous make fragments from "
2132           << Me.m_cmt_config << endl; 
2133
2134      for (int i = 0; i < makes.size (); i++) 
2135        { 
2136          const cmt_string& s = makes[i];
2137          CmtSystem::cmt_string_vector words;
2138          CmtSystem::split (s, '.', words);
2139          if (words.size()>=2)
2140              if (CmtSystem::get_makefile_suffix () == "nmake" && words[1] == "nmake")
2141                      CmtSystem::remove_file (s);
2142              else if (CmtSystem::get_makefile_suffix () == "make" && words[1] == "make")
2143                      CmtSystem::remove_file (s);
2144        }   
2145    } 
2146     //exit(-1);
2147
2148  /*
2149  // cout << "Try a cleanup of the installation area " << endl;
2150
2151    //
2152    //  Try a cleanup of the installation area
2153    //
2154  if (current_use.get_strategy ("InstallArea"))
2155    {
2156      CmtInstallAreaMgr& ia_mgr = CmtInstallAreaMgr::instance ();
2157
2158      //cout << "#IA3>" << endl;
2159
2160      if (current_use.get_strategy ("SetupCleanup"))
2161        {
2162          ia_mgr.config ();
2163        }
2164    }
2165  */
2166
2167  CmtSystem::cd (branch); 
2168
2169  Use& use = Use::current ();
2170
2171  use.set (Me.m_current_package,
2172           Me.m_current_version,
2173           Me.m_current_path,
2174           "",
2175           "");
2176
2177  use.change_path (Me.m_current_path);
2178  use.style     = Me.m_current_style;
2179
2180  //cout << "do_config> current style=" << Me.m_current_style << endl;
2181
2182  Me.m_quiet = true;
2183
2184  if (!reach_current_package ())
2185    {
2186      cout << "Cannot read the requirements file" << endl;
2187      return;
2188    }
2189
2190  install_setup_scripts ();
2191  install_cleanup_scripts ();
2192  install_native_version_file ();
2193
2194  CmtSystem::cd ("..");
2195
2196  Branch::BranchVector& branches = Branch::branches ();
2197
2198  int i;
2199
2200  for (i = 0; i < branches.size (); i++)
2201    {
2202      const Branch& branch = branches[i];
2203      const cmt_string& branch_name = branch.name ();
2204
2205      if (!CmtSystem::test_directory (branch_name))
2206        {
2207          if (!CmtSystem::mkdir (branch_name))
2208            {
2209              cout << "Cannot create the " << branch_name <<" branch" << endl;
2210            }
2211          else
2212            {
2213              cout << "Installing the " << branch_name << " directory" << endl;
2214            }
2215        }
2216      else
2217        {
2218          cout << branch_name << " directory already installed" << endl;
2219        }
2220    }
2221}
2222
2223
2224//----------------------------------------------------------
2225void Cmt::do_relocate (const ArgParser& ap)
2226{
2227  if (CmtLock::check () == CmtLock::locked_by_another_user)
2228    {
2229      CmtError::set (CmtError::conflicting_lock, "relocate>");
2230      return;
2231    }
2232
2233  Use& current_use = Use::current ();
2234
2235  if (Me.m_debug)
2236    {
2237      cout << "Cmt::do_relocate> " << endl;
2238      cout << "pwd "          << CmtSystem::pwd () << endl;
2239      cout << "current_dir "  << Me.m_current_dir << endl;
2240      cout << "default_path " << Me.m_default_path << endl;
2241      cout << "cmt config "   <<
2242          Me.m_current_package << " " <<
2243          Me.m_current_version << " " <<
2244          Me.m_current_path << endl;
2245    }
2246
2247  if (Me.m_current_package == "CMT")     return;
2248  if (Me.m_current_package == "methods") return;
2249
2250  cmt_string branch;
2251
2252  CmtSystem::basename (Me.m_current_dir, branch);
2253
2254  if ((branch != "mgr") && (branch != "cmt"))
2255    {
2256
2257        //
2258        // Here we are in a standalone package (ie completely unstructured)
2259        //
2260
2261      if (CmtSystem::test_file ("requirements"))
2262        {
2263          cout << "------------------------------------------" << endl;
2264          cout << "Configuring environment for standalone package." << endl;
2265          cout << "CMT version " << Me.m_cmt_version << "." << endl;
2266          cout << "System is "   << Me.m_cmt_config << endl;
2267          cout << "------------------------------------------" << endl;
2268
2269          install_test_setup_scripts ();
2270          install_test_cleanup_scripts ();
2271
2272          Generator::build_default_makefile ();
2273        }
2274      else
2275        {
2276          cout << "==============================================" << endl;
2277          cout << "cmt relocate must be operated either upon "
2278            "an existing package" << endl;
2279          cout << " (ie. when a requirements file already exists)" << endl;
2280          cout << "   > cd ..." << endl;
2281          cout << "   > cmt relocate" << endl;
2282          cout << "or to create a new package" << endl;
2283          cout << "   > cmt relocate <package> <version> [<path>]" << endl;
2284          cout << "==============================================" << endl;
2285        }
2286
2287      return;
2288    }
2289
2290  configure_current_package ();
2291
2292  Generator::build_default_makefile ();
2293 
2294  CmtSystem::cd ("..");   
2295  CmtSystem::cd (branch); 
2296
2297  Use& use = Use::current ();
2298
2299  use.set (Me.m_current_package,
2300           Me.m_current_version,
2301           Me.m_current_path,
2302           "",
2303           "");
2304
2305  use.change_path (Me.m_current_path);
2306  use.style     = Me.m_current_style;
2307
2308  Me.m_quiet = true;
2309
2310  if (!reach_current_package ())
2311    {
2312      cout << "Cannot read the requirements file" << endl;
2313      return;
2314    }
2315
2316  install_setup_scripts ();
2317  install_cleanup_scripts ();
2318
2319  CmtSystem::cd ("..");
2320
2321  Branch::BranchVector& branches = Branch::branches ();
2322
2323  int i;
2324
2325  for (i = 0; i < branches.size (); i++)
2326    {
2327      const Branch& branch = branches[i];
2328      const cmt_string& branch_name = branch.name ();
2329
2330      if (!CmtSystem::test_directory (branch_name))
2331        {
2332          if (!CmtSystem::mkdir (branch_name))
2333            {
2334              cout << "Cannot create the " << branch_name <<" branch" << endl;
2335            }
2336          else
2337            {
2338              cout << "Installing the " << branch_name << " directory" << endl;
2339            }
2340        }
2341      else
2342        {
2343          cout << branch_name << " directory already installed" << endl;
2344        }
2345    }
2346}
2347
2348//----------------------------------------------------------
2349void Cmt::do_create (const ArgParser& ap)
2350{
2351  if (ap.arguments.size () < 2) return;
2352
2353  const cmt_string& package = ap.arguments[0];
2354  const cmt_string& version = ap.arguments[1];
2355  cmt_string offset;
2356  if (ap.arguments.size () >= 3) offset = ap.arguments[2];
2357
2358  if (Me.m_debug)
2359    {
2360      cout << "do_create>Me.m_current_package=" << Me.m_current_package << endl;
2361      cout << "do_create>package=" << package << endl;
2362    }
2363
2364    //if (Me.m_current_package == "CMT") return;
2365    //if (Me.m_current_package == "methods") return;
2366
2367  cmt_string the_path;
2368
2369  the_path = CmtSystem::pwd ();
2370
2371  if (offset != "")
2372    {
2373      if (!CmtSystem::absolute_path (offset))
2374        {
2375          // offset is really a relative offset
2376          the_path += CmtSystem::file_separator ();
2377          the_path += offset;
2378        }
2379      else // absolute path
2380        {
2381          the_path = offset;
2382        }
2383    }
2384
2385  CmtSystem::compress_path (the_path);
2386
2387  // Now 'the_path' contains the complete path where the package will be created
2388
2389  cout << "------------------------------------------" << endl;
2390  cout << "Configuring environment for package " << package <<
2391    " version " << version << "." << endl;
2392  cout << "CMT version " << Me.m_cmt_version << "." << endl;
2393  cout << "Root set to " << the_path << "." << endl;
2394  cout << "System is " << Me.m_cmt_config << endl;
2395  cout << "------------------------------------------" << endl;
2396
2397  if (!CmtSystem::test_directory (the_path))
2398    {
2399      if (!CmtSystem::mkdir (the_path))
2400        {
2401          cout << "Cannot create the path directory" << endl;
2402          return;
2403        }
2404      else
2405        {
2406          cout << "Installing the path directory" << endl;
2407        }
2408    }
2409
2410  CmtSystem::cd (the_path);
2411
2412  if (!CmtSystem::test_directory (package))
2413    {
2414      if (!CmtSystem::mkdir (package))
2415        {
2416          cout << "Cannot create the package directory" << endl;
2417          return;
2418        }
2419      else
2420        {
2421          cout << "Installing the package directory" << endl;
2422        }
2423    }
2424  else
2425    {
2426      cout << "Package directory already installed" << endl;
2427    }
2428
2429  CmtSystem::cd (package);
2430
2431  Use& current_use = Use::current ();
2432
2433  bool with_version_dir = current_use.get_strategy ("VersionDirectory");
2434
2435  CmtStructuringStyle style = get_current_structuring_style ();
2436
2437  if (style != default_structuring_style)
2438    {
2439      if (with_version_dir)
2440        {
2441          if (style == without_version_directory)
2442            {
2443              with_version_dir = false;
2444            }
2445        }
2446      else
2447        {
2448          if (style == with_version_directory)
2449            {
2450              with_version_dir = true;
2451            }
2452        }
2453    }
2454
2455  if (with_version_dir)
2456    {
2457      if (!CmtSystem::test_directory (version))
2458        {
2459          if (!CmtSystem::mkdir (version))
2460            {
2461              cout << "Cannot create the version directory" << endl;
2462              return;
2463            }
2464          else
2465            {
2466              cout << "Installing the version directory" << endl;
2467            }
2468        }
2469      else
2470        {
2471          cout << "Version directory already installed" << endl;
2472        }
2473
2474      CmtSystem::cd (version);
2475    }
2476  else
2477    {
2478      cout << "Version directory will not be created due to structuring style" << endl;
2479    }
2480
2481  if (!CmtSystem::test_directory ("cmt"))
2482    {
2483      if (!CmtSystem::test_directory ("mgr"))
2484        {
2485          if (!CmtSystem::mkdir ("cmt"))
2486            {
2487              cout << "Cannot create the cmt directory" << endl;
2488              return;
2489            }
2490          else
2491            {
2492              if (with_version_dir)
2493                {
2494                  Me.m_current_style = cmt_style;
2495                }
2496              else
2497                {
2498                  Me.m_current_style = no_version_style;
2499                }
2500
2501              cout << "Installing the cmt directory" << endl;
2502            }
2503        }
2504      else
2505        {
2506          if (with_version_dir)
2507            {
2508              Me.m_current_style = mgr_style;
2509            }
2510          else
2511            {
2512              Me.m_current_style = no_version_style;
2513            }
2514         
2515          cout << "Mgr directory already installed" << endl;
2516        }
2517    }
2518  else
2519    {
2520      if (with_version_dir)
2521        {
2522          Me.m_current_style = cmt_style;
2523        }
2524      else
2525        {
2526          Me.m_current_style = no_version_style;
2527        }
2528
2529      cout << "Cmt directory already installed" << endl;
2530    }
2531
2532  if (!CmtSystem::test_directory ("src"))
2533    {
2534      if (!CmtSystem::mkdir ("src"))
2535        {
2536          cout << "Cannot create the src directory" << endl;
2537          return;
2538        }
2539      else
2540        {
2541          cout << "Installing the src directory" << endl;
2542        }
2543    }
2544  else
2545    {
2546      cout << "src directory already installed" << endl;
2547    }
2548
2549  switch (Me.m_current_style)
2550    {
2551    case cmt_style:
2552    case no_version_style:
2553      CmtSystem::cd ("cmt");
2554      break;
2555    case mgr_style:
2556      CmtSystem::cd ("mgr");
2557      break;
2558    }
2559
2560  Generator::build_default_makefile ();
2561
2562  if (!CmtSystem::test_file ("requirements"))
2563    {
2564      // create an empty requirement file.
2565      ofstream f ("requirements");
2566      if (f)
2567        {
2568          f << "package " << package << endl;
2569          f << endl;
2570          f.close ();
2571        }
2572    }
2573
2574  if (!with_version_dir)
2575    {
2576      ofstream f ("version.cmt");
2577      if (f)
2578        {
2579          f << version << endl;
2580          f.close ();
2581        }
2582    }
2583
2584  Me.m_current_package = package;
2585  Me.m_current_version = version;
2586  Me.m_current_path    = the_path;
2587  Me.m_current_dir     = CmtSystem::pwd ();
2588
2589  do_config (ap);
2590}
2591
2592//----------------------------------------------------------
2593void Cmt::do_create_project (const ArgParser& ap)
2594{
2595  int argc = ap.arguments.size ();
2596  int arg = 0;
2597
2598  if (argc < 1) return;
2599
2600  cmt_string project;
2601  cmt_string release;
2602  cmt_string path;
2603
2604  project = ap.arguments[arg]; argc--; arg++;
2605
2606  if (argc > 0)
2607    {
2608      release = ap.arguments[arg];
2609
2610      if (release[0] != '-')
2611        {
2612          argc--; 
2613          arg++;
2614          if (argc > 0)
2615            {
2616              path = ap.arguments[arg];
2617              if (path[0] != '-')
2618                {
2619                  argc--; arg++;
2620                }
2621              else
2622                {
2623                  path = "";
2624                }
2625            }
2626        }
2627      else
2628        {
2629          release = "";
2630        }
2631    }
2632
2633  if (Project::create (project, release, path))
2634    {
2635      while (argc > 0)
2636        {
2637          const cmt_string& argument = ap.arguments[arg]; argc--; arg++;
2638         
2639          if (argument.substr (0, 5) == "-use=")
2640            {
2641              cmt_string use;
2642
2643              argument.substr (5, use);
2644
2645              CmtSystem::cmt_string_vector words;
2646              CmtSystem::split (use, ":", words);
2647
2648              ofstream f (Project::get_project_file_name (), ios_base::app);
2649              if (f)
2650                {
2651                  f << "use " << words[0] << " " << words[1] << " " << words[2] << endl;
2652                  f << endl;
2653                  f.close ();
2654                }
2655            }
2656        }
2657    }
2658}
2659
2660//----------------------------------------------------------
2661void Cmt::do_cvsbranches (const ArgParser& ap)
2662{
2663  Cvs::branches (ap.arguments[0]);
2664}
2665
2666//----------------------------------------------------------
2667void Cmt::do_cvssubpackages (const ArgParser& ap)
2668{
2669  Cvs::subpackages (ap.arguments[0]);
2670}
2671
2672//----------------------------------------------------------
2673void Cmt::do_cvssubprojects (const ArgParser& ap)
2674{
2675  Cvs::subprojects (ap.arguments[0]);
2676}
2677
2678//----------------------------------------------------------
2679void Cmt::do_cvstags (const ArgParser& ap)
2680{
2681  Cvs::tags (ap.arguments);
2682}
2683
2684//----------------------------------------------------------
2685void Cmt::do_do (const ArgParser& ap)
2686{
2687  if (ap.arguments.size () > 0) 
2688    {
2689      set_standard_macros ();
2690      Cmt::reset_all_sets_done ();
2691      Symbol::all_set ();
2692      Generator::build_default_makefile ();
2693
2694      Symbol* symbol = Symbol::find (ap.arguments[0]);
2695
2696      if (symbol == 0)
2697        {
2698          Me.m_action = action_show_action_names;
2699          /*
2700          if (!Me.m_quiet)
2701            {
2702              cerr << "Existing actions:" << endl;
2703              print_symbol_names (ap.mode);
2704            }
2705          */
2706          CmtError::set (CmtError::unknown_command, ap.arguments[0]);
2707          return;
2708        }
2709
2710      /*
2711        We convert extra arguments into the standard macro cmt_args
2712      */
2713
2714      cmt_string args;
2715
2716      for (int i = 1; i < ap.arguments.size (); i++)
2717        {
2718          cmt_string s = ap.arguments[i];
2719          if (i > 1) args += " ";
2720          args += s;
2721        }
2722
2723      cmt_string r = "macro cmt_args \"";
2724      r += args;
2725      r += "\"";
2726
2727      Use* current_use = &(Use::current ());
2728     
2729      SyntaxParser::parse_requirements_line (r, current_use);
2730
2731      cmt_string cmd = symbol->build_macro_value ();
2732      Symbol::expand (cmd);
2733
2734      cout << "Execute action " << ap.arguments[0] << " => " << cmd << endl;
2735
2736      int status = CmtSystem::execute (cmd);
2737      if (status != 0)
2738        CmtError::set (CmtError::execution_failed, ap.arguments[0], status);
2739     
2740    }
2741}
2742
2743//----------------------------------------------------------
2744void Cmt::do_expand_model (const ArgParser& ap)
2745{
2746  set_standard_macros ();
2747
2748  if ((ap.arguments[0] == "-strict") && (ap.arguments.size () > 1))
2749    {
2750      CmtModel::strict_expand (ap.arguments[1]);
2751    }
2752  else if ((ap.arguments[0] == "-test") && (ap.arguments.size () > 2))
2753    {
2754      CmtModel::test_regexp (ap.arguments[1], ap.arguments[2]);
2755    }
2756  else if (ap.arguments.size () > 0)
2757    {
2758      CmtModel::expand (ap.arguments[0]);
2759    }
2760}
2761
2762/**
2763 *  Handle free filtering of text files containing $(xxx) or ${xxx} patterns
2764 *
2765 *  Substitution is performed against CMT macros and environment variables.
2766 *
2767 *  Arguments:
2768 *
2769 *    cmt filter input-file-name output-file-name
2770 *
2771 */
2772void Cmt::do_filter (const ArgParser& ap)
2773{
2774  if (ap.arguments.size () < 2) return;
2775
2776  cmt_string& input = ap.arguments[0];
2777  cmt_string& output = ap.arguments[1];
2778
2779  if (!CmtSystem::test_file (input))
2780    {
2781      cerr << "#CMT> File " << input << " not found" << endl;
2782      return;
2783    }
2784
2785  cmt_string text;
2786
2787  text.read (input);
2788
2789  set_standard_macros ();
2790
2791  Symbol::expand (text);
2792
2793  FILE* file = fopen (output, "wb");
2794  if (file == NULL)
2795    {
2796      cerr << "#CMT> Cannot write filtered file " << output << endl;
2797    }
2798  else
2799    {
2800      text.write (file);
2801      fclose (file);
2802    }
2803}
2804
2805//----------------------------------------------------------
2806void Cmt::do_help (const ArgParser& ap)
2807{
2808  //cerr << "ap.help_action=" << ap.help_action << " Me.m_action=" << Me.m_action << endl;
2809  if (Me.m_action == action_none)
2810    {
2811      CommandHelp::show_all ();
2812    }
2813  else
2814    {
2815      CommandHelp::show (Me.m_action);
2816    }
2817}
2818
2819//----------------------------------------------------------
2820void Cmt::do_lock (const ArgParser& ap)
2821{
2822  const cmt_string& package = Me.m_current_package;
2823  const cmt_string& version = Me.m_current_version;
2824  const cmt_string& path    = Me.m_current_path;
2825
2826  //(unsused) Use& use = Use::current();
2827
2828  cout << "try to lock package " << package << " in " << CmtSystem::pwd () << endl;
2829
2830  set_standard_macros ();
2831
2832  CmtLock::status status = CmtLock::lock ();
2833}
2834
2835//----------------------------------------------------------
2836void Cmt::do_remove (const ArgParser& ap)
2837{
2838  const cmt_string& package = Me.m_current_package;
2839  const cmt_string& version = Me.m_current_version;
2840  const cmt_string& path    = Me.m_current_path;
2841
2842    //Use::UsePtrVector& Uses = Use::get_ordered_uses ();
2843
2844  if (Me.m_current_package == "CMT") return;
2845  if (Me.m_current_package == "methods") return;
2846
2847  cmt_string the_path;
2848
2849  //the_path = Me.m_default_path;
2850  the_path = CmtSystem::pwd ();
2851
2852  if (path != "")
2853    {
2854      if (!CmtSystem::absolute_path (path))
2855        {
2856          // path is just a suffix
2857          the_path += CmtSystem::file_separator ();
2858          the_path += path;
2859        }
2860      else // absolute path
2861        {
2862          the_path = path;
2863        }
2864    }
2865
2866  CmtSystem::compress_path (the_path);
2867
2868  cout << "------------------------------------------" << endl;
2869  cout << "Removing package " << package <<
2870    " version " << version << "." << endl;
2871  cout << "CMT version " << Me.m_cmt_version << "." << endl;
2872  cout << "Root set to " << the_path << "." << endl;
2873  cout << "System is " << Me.m_cmt_config << endl;
2874  cout << "------------------------------------------" << endl;
2875
2876  the_path += CmtSystem::file_separator ();
2877  the_path += package;
2878
2879  if (!CmtSystem::cd (the_path))
2880    {
2881      cout << "Path " << the_path << " not reachable" << endl;
2882      return;
2883    }
2884
2885  if (CmtSystem::test_directory (version))
2886    {
2887      if (CmtSystem::remove_directory (version))
2888        {
2889          cout << "Version " << version << " has been removed from " << the_path << endl;
2890          CmtSystem::cmt_string_vector contents;
2891          CmtSystem::scan_dir (".", contents);
2892          if (contents.size () == 0)
2893            {
2894              CmtSystem::cd ("..");
2895              if (CmtSystem::remove_directory (package))
2896                {
2897                  cout << "Package " << package << " has no more versions. Thus it has been removed."<< endl;
2898                }
2899            }
2900        }
2901      else
2902        {
2903          cout << "Impossible to remove version " << version << " from " << the_path << endl;
2904        }
2905    }
2906  else if (CmtSystem::test_directory ("cmt"))
2907    {
2908      CmtSystem::cd ("cmt");
2909
2910      cmt_string v;
2911
2912      v.read ("version.cmt");
2913      if (v == version)
2914        {
2915          CmtSystem::cd ("..");
2916          if (!CmtSystem::remove_directory ("cmt"))
2917            {
2918              cout << "Unstructured version " << version
2919                   << " has been removed from " << the_path << endl;
2920            }
2921          else
2922            {
2923              cout << "Impossible to remove unstructured version " << version
2924                   << " from " << the_path << endl;
2925            }
2926        }
2927      else
2928        {
2929          cout << "Version " << version << " not found" << endl;
2930        }
2931    }
2932  else
2933    {
2934      cout << "Version " << version << " not found" << endl;
2935    }
2936}
2937
2938//----------------------------------------------------------
2939void Cmt::do_remove_library_links (const ArgParser& ap)
2940{
2941  if (CmtLock::check () == CmtLock::locked_by_another_user)
2942    {
2943      CmtError::set (CmtError::conflicting_lock, "remove_library_links>");
2944      return;
2945    }
2946
2947  set_standard_macros ();
2948
2949  Use::UsePtrVector& Uses = Use::get_ordered_uses ();
2950  Use& current_use = Use::current ();
2951  int i;
2952  cmt_string shlibsuffix;
2953  cmt_string symunlink;
2954
2955  {
2956    Symbol* macro = Symbol::find ("shlibsuffix");
2957    if (macro == 0) return;
2958    shlibsuffix = macro->build_macro_value ();
2959    Symbol::expand (shlibsuffix);
2960  }
2961
2962  {
2963    Symbol* macro = Symbol::find ("symunlink");
2964    if (macro == 0) return;
2965    symunlink = macro->build_macro_value ();
2966    Symbol::expand (symunlink);
2967  }
2968
2969  for (i = 0; i < Uses.size (); i++)
2970    {
2971      Use* use = Uses[i];
2972
2973      if (use->discarded) continue;
2974      if (use->m_hidden) continue;
2975
2976      if (!use->located ())
2977        {
2978          if (!Me.m_quiet)
2979            {
2980              cerr << "#CMT> package " << use->get_package_name () <<
2981                  " " << use->version << " " << use->path << 
2982                  " not found" <<
2983                  endl;
2984            }
2985        }
2986      else
2987        {
2988          if (use->get_package_name () == "CMT") continue;
2989          if (use->get_package_name () == current_use.get_package_name ()) continue;
2990
2991          cmt_string s;
2992
2993          s = use->get_package_name ();
2994          s += "_libraries";
2995
2996          Symbol* libraries_macro = Symbol::find (s);
2997
2998          if (libraries_macro == 0) continue;
2999
3000          cmt_string libraries = libraries_macro->build_macro_value ();
3001          Symbol::expand (libraries);
3002
3003          static CmtSystem::cmt_string_vector values;
3004
3005          CmtSystem::split (libraries, " \t", values);
3006
3007          for (int j = 0; j < values.size (); j++)
3008            {
3009              const cmt_string& library = values[j];
3010
3011              static cmt_string libname;
3012              static cmt_string name;
3013
3014              // Is it a simple name or a complete path?
3015
3016              libname = library;
3017              Symbol::expand (libname);
3018
3019              if (CmtSystem::absolute_path (libname))
3020                {
3021                  /**
3022                   *   We assume here that "library" contains a complete path.
3023                   *   (including the complete syntax libxxx.so)
3024                   */
3025
3026                  cmt_string suffix;
3027                  CmtSystem::basename (library, name);
3028                }
3029              else
3030                {
3031                  /**
3032                   *   Here we expect that only the base name of the library
3033                   *   is given : ie it should not contain the "lib" prefix,
3034                   *   nor the suffix .so, nor any path prefix.
3035                   *    This of course should generally correspond to a constituent name.
3036                   */
3037
3038                  name = "lib";
3039                  name += libname;
3040                  name += ".";
3041                  name += shlibsuffix;
3042                }
3043
3044              Symbol::expand (libname);
3045
3046              if (current_use.get_strategy ("InstallArea"))
3047                {
3048                  const CmtInstallAreaMgr& ia_mgr = CmtInstallAreaMgr::instance ();
3049
3050                  //cout << "#IA4>" << endl;
3051
3052                  cmt_string s1 = ia_mgr.get_installarea ();
3053
3054                  {
3055                    Symbol* symbol = Symbol::find ("CMTINSTALLAREA");
3056                    if (symbol != 0)
3057                      {
3058                        s1 = symbol->build_macro_value ();
3059                        Symbol::expand (s1);
3060                      }
3061                  }
3062                 
3063                  cmt_string s2;
3064
3065                  {
3066                    Symbol* macro = Symbol::find ("tag");
3067                    if (macro != 0)
3068                      {
3069                        s2 = macro->build_macro_value ();
3070                        Symbol::expand (s2);
3071                      }
3072                  }
3073
3074                    // Now deleting the reference file
3075
3076                  s = symunlink;
3077                  s += " ";
3078                  s += s1;
3079                  s += CmtSystem::file_separator ();
3080                  s += s2;
3081                  s += CmtSystem::file_separator ();
3082                  s += "lib";
3083                  s += CmtSystem::file_separator ();
3084                  s += name;
3085                  s += ".cmtref";
3086                  s += " ";
3087                  s += s1;
3088                  s += CmtSystem::file_separator ();
3089                  s += s2;
3090                  s += CmtSystem::file_separator ();
3091                  s += "lib";
3092                  s += CmtSystem::file_separator ();
3093                  s += name;
3094                }
3095              else
3096                {
3097                  s = symunlink;
3098                  s += " ../$(";
3099                  s += current_use.get_package_name ();
3100                  s += "_tag)/";
3101                  s += name;
3102                }
3103
3104              Symbol::expand (s);
3105
3106              if (!Me.m_quiet) cout << s << endl;
3107              int status = CmtSystem::execute (s);
3108
3109              if (status != 0)
3110                {
3111                  if (status != 2) CmtError::set (CmtError::execution_error, s);
3112
3113                  cerr << "#CMT> Cannot remove the symbolic link " << s << endl;
3114
3115                  break;
3116                }
3117            }
3118        }
3119    }
3120}
3121
3122//----------------------------------------------------------
3123void Cmt::do_run (const ArgParser& ap)
3124{
3125  if (ap.arguments.size () > 0) 
3126    {
3127      set_standard_macros ();
3128      Cmt::reset_all_sets_done ();
3129      Symbol::all_set ();
3130
3131      cmt_string cmd;
3132
3133      for (int i = 0; i < ap.arguments.size (); i++)
3134        {
3135          cmd += ap.arguments[i];
3136          cmd += " ";
3137        }
3138
3139      CmtSystem::execute (cmd);
3140    }
3141}
3142
3143//----------------------------------------------------------
3144void Cmt::do_run_sequence (const ArgParser& ap)
3145{
3146  if (ap.arguments.size () == 0) cerr << "#CMT> run_sequence: no sequence specified" << endl;
3147
3148  SequenceRunner runner;
3149
3150  cout << "# cmt run_sequence: sequence " << ap.arguments[0] << endl;
3151
3152  runner.run (ap.arguments[0]);
3153}
3154
3155//----------------------------------------------------------
3156void Cmt::do_set_version (const ArgParser& ap)
3157{
3158  if (ap.arguments.size () == 0) cerr << "#CMT> set version: no version specified" << endl;
3159
3160  const cmt_string& version = ap.arguments[0];
3161
3162  int v, r, p;
3163
3164  if (!CmtSystem::is_version_directory (version, v, r, p))
3165    {
3166      cerr << "#CMT> set version " << version << " is not a correct version syntax" << endl;
3167      return;
3168    }
3169
3170  if ((v == -1) || (r == -1) || (p == -1))
3171    {
3172      cerr << "#CMT> set version " << version
3173           << " You cannot use wild card to set a version" << endl;
3174      return;
3175    }
3176
3177  // We want to install the version.cmt file
3178
3179  // We first check we are in a cmt branch
3180  cmt_string h = CmtSystem::pwd ();
3181  cmt_string branch;
3182  CmtSystem::basename (h, branch);
3183
3184  if (branch != "cmt")
3185    {
3186      cerr << "#CMT> set version " << version << " must be applied in a cmt directory" 
3187           << endl;
3188      return;
3189    }
3190
3191  CmtSystem::dirname (h, h);
3192  CmtSystem::basename (h, branch);
3193
3194  if (branch == version)
3195    {
3196      cerr << "#CMT> set version " << version << " is already available as a version directory" 
3197           << endl;
3198      return;
3199    }
3200
3201  cout << "Writing version file : " << version << endl;
3202
3203  version.write ("version.cmt");
3204}
3205
3206//----------------------------------------------------------
3207void Cmt::do_set_versions (const ArgParser& ap)
3208{
3209  CmtSystem::cmt_string_vector args;
3210
3211  args = ap.arguments;
3212  {
3213    cmt_string& s = args.add ();
3214    s = "cmt";
3215  }
3216  {
3217    cmt_string& s = args.add ();
3218    s = "set";
3219  }
3220  {
3221    cmt_string& s = args.add ();
3222    s = "version";
3223  }
3224  {
3225    cmt_string& s = args.add ();
3226    s = "<version>";
3227  }
3228
3229  Me.m_action = action_broadcast;
3230
3231  do_broadcast (ap);
3232}
3233
3234//----------------------------------------------------------
3235void Cmt::do_setup (const ArgParser& ap)
3236{
3237  Use& current_use = Use::current ();
3238
3239  do_check_configuration (ap);
3240
3241  print (ap.mode);
3242
3243    //
3244    //  Try a cleanup of the installation area
3245    //
3246  if (current_use.get_strategy ("InstallArea"))
3247    {
3248      CmtInstallAreaMgr& ia_mgr = CmtInstallAreaMgr::instance ();
3249
3250      //cout << "#IA5>" << endl;
3251
3252      ia_mgr.setup ();
3253
3254      /*
3255      if (current_use.get_strategy ("SetupCleanup"))
3256        {
3257          const cmt_string& installarea = ia_mgr.get_installarea ();
3258
3259          if (installarea != "")
3260            {
3261              cmt_string q;
3262             
3263              switch (mode)
3264                {
3265                case Sh :
3266                case Csh :
3267                  q = "\'";
3268                  break;
3269                default :
3270                  break;
3271                }
3272             
3273              if (!Me.m_quiet)
3274                {
3275                  cout << "echo "  << q
3276                       << "# Doing cleanup in the installation area " << installarea
3277                       << q << endl;
3278                }
3279            }
3280
3281          ia_mgr.config ();
3282        }
3283      */
3284    }
3285}
3286
3287//----------------------------------------------------------
3288void Cmt::do_show_action (const ArgParser& ap)
3289{
3290  cmt_string target;
3291
3292  if (ap.arguments.size () > 0) target = ap.arguments[0];
3293
3294  Symbol* symbol;
3295
3296  set_standard_macros ();
3297
3298  symbol = Symbol::find (target);
3299
3300  if (symbol == 0) 
3301    {
3302      cmt_string t = " ";
3303      t += target;
3304      t += " is not defined ";
3305
3306      CmtError::set (CmtError::symbol_not_found, t);
3307
3308      return;
3309    }
3310  else
3311    {
3312      cmt_string t = target;
3313      t += " is a ";
3314
3315      if ((Me.m_action == action_show_action) ||
3316          (Me.m_action == action_show_action_value))
3317        {
3318          if (symbol->type != Symbol::SymbolAction)
3319            {
3320              if (symbol->type == Symbol::SymbolMacro)
3321                {
3322                  t += "macro";
3323                }
3324              else if (symbol->type == Symbol::SymbolSet)
3325                {
3326                  t += "set";
3327                }
3328              else if (symbol->type == Symbol::SymbolPath)
3329                {
3330                  t += "path";
3331                }
3332              else if (symbol->type == Symbol::SymbolAlias)
3333                {
3334                  t += "alias";
3335                }
3336
3337              CmtError::set (CmtError::warning, t);
3338            }
3339        }
3340    }
3341
3342  if (symbol->value_lists.size () < 1) return;
3343
3344  symbol->show_macro (ap.mode);
3345}
3346
3347//----------------------------------------------------------
3348void Cmt::do_show_action_names (const ArgParser& ap)
3349{
3350  if (ap.arguments.size () > 0)
3351    {
3352      const cmt_string& pattern = ap.arguments[0];
3353      print_symbol_names (ap.mode, pattern);
3354    }
3355  else
3356    {
3357      print_symbol_names (ap.mode);
3358    }
3359}
3360
3361//----------------------------------------------------------
3362void Cmt::do_show_action_value (const ArgParser& ap)
3363{
3364  do_show_macro (ap);
3365}
3366
3367//----------------------------------------------------------
3368void Cmt::do_show_actions (const ArgParser& ap)
3369{
3370  if (ap.arguments.size () > 0)
3371    {
3372      const cmt_string& pattern = ap.arguments[0];
3373      print_macros (ap.mode, pattern);
3374    }
3375  else
3376    {
3377      print_macros (ap.mode);
3378    }
3379}
3380
3381//----------------------------------------------------------
3382void Cmt::do_show_all_tags (const ArgParser& /*ap*/)
3383{
3384  Tag::TagPtrVector tags = Tag::tags ();
3385  int index;
3386
3387  set_standard_macros ();
3388
3389  for (index = 0; index < tags.size (); index++)
3390    {
3391      const Tag* tag = tags[index];
3392      if (tag != 0)
3393        {
3394          tag->show_definition (true);
3395        }
3396    }
3397}
3398
3399//----------------------------------------------------------
3400void Cmt::do_show_applied_patterns (const ArgParser& /*ap*/)
3401{
3402  Pattern::show_all_applied_patterns ();
3403}
3404
3405//----------------------------------------------------------
3406void Cmt::do_show_author (const ArgParser& /*ap*/)
3407{
3408  Use& use = Use::current();
3409
3410  cout << use.author << endl;
3411 
3412}
3413//----------------------------------------------------------
3414void Cmt::do_show_project_author (const ArgParser& /*ap*/)
3415{
3416  cmt_string cmtpath;
3417  cmt_string offset;
3418  cmt_string pauthor = "";
3419
3420  Use& use = Use::current();   
3421  use.get_cmtpath_and_offset (cmtpath, offset);
3422  Project* p = Project::find_by_cmtpath (cmtpath);
3423
3424  cout <<p->get_author ()<<endl;
3425
3426}
3427
3428//----------------------------------------------------------
3429void Cmt::do_show_branches (const ArgParser& ap)
3430{
3431  Branch::print_all (ap.mode);
3432}
3433
3434//----------------------------------------------------------
3435void Cmt::do_show_clients (const ArgParser& ap)
3436{
3437  cmt_string package   = "";
3438  cmt_string version   = "";
3439  cmt_string path_name = "";
3440
3441  if (ap.arguments.size () >= 1) package  = ap.arguments[0];
3442  if (ap.arguments.size () >= 2) version  = ap.arguments[1];
3443  if (ap.arguments.size () >= 3) path_name = ap.arguments[2];
3444
3445  PathScanner scanner;
3446  ClientCollector collector (package, version);
3447
3448  clear     ();
3449  configure ();
3450
3451  cout << "# ----------- Clients of " << package <<
3452    " " << version <<
3453    " " << path_name <<
3454    endl;
3455
3456  if (path_name == "")
3457    {
3458      Project::scan_paths (scanner, collector);
3459    }
3460  else
3461    {
3462      scanner.scan_path (path_name, collector);
3463    }
3464  cout << "# ----------- " << collector.count () << " clients found." << endl;
3465}
3466
3467//----------------------------------------------------------
3468void Cmt::do_show_cmtpath_patterns (const ArgParser& /*ap*/)
3469{
3470  set_standard_macros ();
3471  CmtPathPattern::show_all ();
3472}
3473
3474//----------------------------------------------------------
3475void Cmt::do_show_constituent (const ArgParser& ap)
3476{
3477  if (ap.arguments.size () > 0) 
3478    {
3479      set_standard_macros ();
3480
3481      Constituent* c = Constituent::find (ap.arguments[0]);
3482      if (c != 0)
3483        {
3484          c->show ();
3485        }
3486    }
3487}
3488
3489//----------------------------------------------------------
3490void Cmt::do_show_constituent_names (const ArgParser& /*ap*/)
3491{
3492  set_standard_macros ();
3493  Constituent::show_names ();
3494}
3495
3496//----------------------------------------------------------
3497void Cmt::do_show_constituents (const ArgParser& /*ap*/)
3498{
3499  set_standard_macros ();
3500  Constituent::show_all ();
3501}
3502
3503//----------------------------------------------------------
3504void Cmt::do_show_cycles (const ArgParser& /*ap*/)
3505{
3506  set_standard_macros ();
3507  Use& use = Use::current();
3508
3509  use.show_cycles ();
3510}
3511
3512//----------------------------------------------------------
3513void Cmt::do_show_fragment (const ArgParser& ap)
3514{
3515  if (ap.arguments.size () > 0) Fragment::show (ap.arguments[0]);
3516}
3517
3518//----------------------------------------------------------
3519void Cmt::do_show_fragments (const ArgParser& /*ap*/)
3520{
3521  Fragment::show_all ();
3522}
3523
3524//----------------------------------------------------------
3525void Cmt::do_show_groups (const ArgParser& /*ap*/)
3526{
3527  Group::show_all ();
3528}
3529
3530//----------------------------------------------------------
3531void Cmt::do_show_include_dirs (const ArgParser& /*ap*/)
3532{
3533  cmt_string temp;
3534
3535  Use& use = Use::current();
3536
3537  set_standard_macros ();
3538
3539  if (use.include_path == "")
3540    {
3541      temp += "$(src) ";
3542    }
3543  else if (use.include_path != "none")
3544    {
3545      temp += use.include_path;
3546      temp += " ";
3547    }
3548
3549  for (int include_number = 0;
3550       include_number < use.includes.size ();
3551       include_number++)
3552    {
3553      Include& incl = use.includes[include_number];
3554
3555      if (incl.name == "") continue;
3556
3557      temp += incl.name;
3558      temp += " ";
3559    }
3560
3561  cout << temp << endl;
3562}
3563
3564//----------------------------------------------------------
3565void Cmt::do_show_language (const ArgParser& ap)
3566{
3567  if (ap.arguments.size () > 0) 
3568    {
3569      set_standard_macros ();
3570      Language::show (ap.arguments[0]);
3571    }
3572}
3573
3574//----------------------------------------------------------
3575void Cmt::do_show_languages (const ArgParser& /*ap*/)
3576{
3577  set_standard_macros ();
3578  Language::show_all ();
3579}
3580
3581//----------------------------------------------------------
3582void Cmt::do_show_macro (const ArgParser& ap)
3583{
3584  cmt_string target;
3585
3586  if (ap.arguments.size () > 0) target = ap.arguments[0];
3587
3588  Symbol* symbol;
3589
3590  set_standard_macros ();
3591
3592  symbol = Symbol::find (target);
3593
3594  if (symbol == 0) 
3595    {
3596      cmt_string t = " ";
3597      t += target;
3598      t += " is not defined ";
3599
3600      CmtError::set (CmtError::symbol_not_found, t);
3601
3602      return;
3603    }
3604  else
3605    {
3606      cmt_string t = target;
3607      t += " is a ";
3608
3609      if ((Me.m_action == action_show_macro) ||
3610          (Me.m_action == action_show_macro_value))
3611        {
3612          if (symbol->type != Symbol::SymbolMacro)
3613            {
3614              if (symbol->type == Symbol::SymbolAction)
3615                {
3616                  t += "action";
3617                }
3618              else if (symbol->type == Symbol::SymbolSet)
3619                {
3620                  t += "set";
3621                }
3622              else if (symbol->type == Symbol::SymbolPath)
3623                {
3624                  t += "path";
3625                }
3626              else if (symbol->type == Symbol::SymbolAlias)
3627                {
3628                  t += "alias";
3629                }
3630
3631              CmtError::set (CmtError::warning, t);
3632            }
3633        }
3634      else if ((Me.m_action == action_show_set) ||
3635               (Me.m_action == action_show_set_value))
3636        {
3637          if ((symbol->type != Symbol::SymbolSet) &&
3638              (symbol->type != Symbol::SymbolPath) &&
3639              (symbol->type != Symbol::SymbolAction) &&
3640              (symbol->type != Symbol::SymbolAlias))
3641            {
3642              t += "macro";
3643
3644              CmtError::set (CmtError::warning, t);
3645            }
3646        }
3647    }
3648
3649  if (symbol->value_lists.size () < 1) return;
3650
3651  symbol->show_macro (ap.mode);
3652}
3653
3654//----------------------------------------------------------
3655void Cmt::do_show_macro_names (const ArgParser& ap)
3656{
3657  if (ap.arguments.size () > 0)
3658    {
3659      const cmt_string& pattern = ap.arguments[0];
3660      print_symbol_names (ap.mode, pattern);
3661    }
3662  else
3663    {
3664      print_symbol_names (ap.mode);
3665    }
3666}
3667
3668//----------------------------------------------------------
3669void Cmt::do_show_macro_value (const ArgParser& ap)
3670{
3671  do_show_macro (ap);
3672}
3673
3674//----------------------------------------------------------
3675void Cmt::do_show_macros (const ArgParser& ap)
3676{
3677  if (ap.arguments.size () > 0)
3678    {
3679      const cmt_string& pattern = ap.arguments[0];
3680      print_macros (ap.mode, pattern);
3681    }
3682  else
3683    {
3684      print_macros (ap.mode);
3685    }
3686}
3687
3688//----------------------------------------------------------
3689void Cmt::do_show_manager (const ArgParser& /*ap*/)
3690{
3691  Use& use = Use::current();
3692
3693  cout << use.manager << endl;
3694}
3695
3696//----------------------------------------------------------
3697void Cmt::do_show_packages (const ArgParser& ap)
3698{
3699  cmt_string path_name;
3700
3701  if (ap.arguments.size () > 0) path_name = ap.arguments[0];
3702
3703  PathScanner   scanner;
3704  PackageViewer viewer;
3705
3706  if (path_name == "")
3707    {
3708      Project::scan_paths (scanner, viewer);
3709    }
3710  else
3711    {
3712      scanner.scan_path (path_name, viewer);
3713    }
3714}
3715
3716//----------------------------------------------------------
3717void Cmt::do_show_path (const ArgParser& /*ap*/)
3718{
3719  Project::show_paths ();
3720}
3721
3722//----------------------------------------------------------
3723void Cmt::do_show_pattern (const ArgParser& ap)
3724{
3725  cmt_string name;
3726  if (ap.arguments.size () > 0) name = ap.arguments[0];
3727  Pattern::show (name);
3728}
3729
3730//----------------------------------------------------------
3731void Cmt::do_show_pattern_names (const ArgParser& /*ap*/)
3732{
3733  Pattern::show_all_names ();
3734}
3735
3736//----------------------------------------------------------
3737void Cmt::do_show_patterns (const ArgParser& /*ap*/)
3738{
3739  Pattern::show_all ();
3740}
3741
3742//----------------------------------------------------------
3743void Cmt::do_show_projects (const ArgParser& /*ap*/)
3744{
3745  Project::show_all ();
3746}
3747
3748//----------------------------------------------------------
3749void Cmt::do_show_pwd (const ArgParser& /*ap*/)
3750{
3751  cout << Me.m_current_dir << endl;
3752}
3753
3754//----------------------------------------------------------
3755void Cmt::do_show_setup (const ArgParser& ap)
3756{
3757  cout << "----------> uses" << endl;
3758  do_show_uses (ap);
3759
3760  cout << "----------> tags" << endl;
3761  do_show_tags (ap);
3762
3763  cout << "----------> CMTPATH" << endl;
3764  do_show_path (ap);
3765}
3766
3767//----------------------------------------------------------
3768void Cmt::do_show_set (const ArgParser& ap)
3769{
3770  do_show_macro (ap);
3771}
3772
3773//----------------------------------------------------------
3774void Cmt::do_show_set_names (const ArgParser& ap)
3775{
3776  if (ap.arguments.size () > 0)
3777    {
3778      const cmt_string& pattern = ap.arguments[0];
3779      print_symbol_names (ap.mode, pattern);
3780    }
3781  else
3782    {
3783      print_symbol_names (ap.mode);
3784    }
3785}
3786
3787//----------------------------------------------------------
3788void Cmt::do_show_set_value (const ArgParser& ap)
3789{
3790  do_show_macro (ap);
3791}
3792
3793//----------------------------------------------------------
3794void Cmt::do_show_sets (const ArgParser& ap)
3795{
3796  if (ap.arguments.size () > 0)
3797    {
3798      const cmt_string& pattern = ap.arguments[0];
3799      print_macros (ap.mode, pattern);
3800    }
3801  else
3802    {
3803      print_macros (ap.mode);
3804    }
3805}
3806
3807//----------------------------------------------------------
3808void Cmt::do_show_strategies (const ArgParser& /*ap*/)
3809{
3810  Use& current_use = Use::current ();
3811
3812  Project::show_specified_strategies_for_all ();
3813
3814  Project* p = Project::get_current ();
3815
3816  /*
3817    if (p != 0) p->show ();
3818    else cout << "No current project" << endl;
3819  */
3820
3821  cout << "Build strategy     : ";
3822
3823  if (current_use.get_strategy ("BuildPrototypes"))
3824    {
3825      cout << "prototypes";
3826    }
3827  else
3828    {
3829      cout << "no_prototypes";
3830    }
3831 
3832  if (current_use.get_strategy ("InstallArea"))
3833    {
3834      cout << " with_installarea";
3835    }
3836  else
3837    {
3838      cout << " without_installarea";
3839    }
3840 
3841  cout << endl;
3842
3843  cout << "Setup strategy     : ";
3844 
3845  if (current_use.get_strategy ("SetupConfig"))
3846    {
3847      cout << "config";
3848    }
3849  else
3850    {
3851      cout << "no_config";
3852    }
3853 
3854  if (current_use.get_strategy ("SetupRoot"))
3855    {
3856      cout << " root";
3857    }
3858  else
3859    {
3860      cout << " no_root";
3861    }
3862 
3863  if (current_use.get_strategy ("SetupCleanup"))
3864    {
3865      cout << " cleanup";
3866    }
3867  else
3868    {
3869      cout << " no_cleanup";
3870    }
3871
3872  cout << endl;
3873 
3874  cout << "Structure strategy : ";
3875 
3876  if (current_use.get_strategy ("VersionDirectory"))
3877    {
3878      cout << "with_version_directory";
3879    }
3880  else
3881    {
3882      cout << "without_version_directory";
3883    }
3884 
3885  cout << endl;
3886
3887  if (Me.m_current_structuring_style != default_structuring_style)
3888    {
3889      cout << "Structuring style  : ";
3890
3891      switch (Me.m_current_structuring_style)
3892        {
3893        case without_version_directory:
3894          cout << "without_version_directory";
3895          break;
3896        case with_version_directory:
3897          cout << "with_version_directory";
3898          break;
3899        }
3900
3901      cout << endl;
3902    }
3903}
3904
3905//----------------------------------------------------------
3906void Cmt::do_show_tags (const ArgParser& /*ap*/)
3907{
3908  Tag::TagPtrVector tags = Tag::tags ();
3909  int index;
3910
3911  set_standard_macros ();
3912
3913  for (index = 0; index < tags.size (); index++)
3914    {
3915      const Tag* tag = tags[index];
3916      if (tag != 0)
3917        {
3918          tag->show (Me.m_quiet);
3919        }
3920    }
3921}
3922
3923//----------------------------------------------------------
3924void Cmt::do_show_use_paths (const ArgParser& ap)
3925{
3926  const cmt_string& to_name = ap.arguments[0];
3927
3928  Use* current = &(Use::current());
3929
3930  current->get_all_clients (to_name);
3931}
3932
3933//----------------------------------------------------------
3934void Cmt::do_show_uses (const ArgParser& /*ap*/)
3935{
3936  Use::show_all ();
3937}
3938
3939//----------------------------------------------------------
3940void Cmt::do_show_version (const ArgParser& /*ap*/)
3941{
3942  cout << Me.m_current_version << endl;
3943}
3944
3945//----------------------------------------------------------
3946void Cmt::do_show_versions (const ArgParser& ap)
3947{
3948  cmt_string package_name;
3949
3950  if (ap.arguments.size () > 0) package_name = ap.arguments[0];
3951
3952  PathScanner scanner;
3953
3954  Project::scan_paths_for_package (scanner, package_name);
3955}
3956
3957//----------------------------------------------------------
3958void Cmt::do_show_system (const ArgParser& /*ap*/)
3959{
3960  cout << CmtSystem::get_cmt_config () << endl;
3961}
3962
3963//----------------------------------------------------------
3964void Cmt::do_unlock (const ArgParser& /*ap*/)
3965{
3966  const cmt_string& package = Me.m_current_package;
3967  const cmt_string& version = Me.m_current_version;
3968  const cmt_string& path    = Me.m_current_path;
3969
3970  // (unused??) Use& use = Use::current();
3971
3972  cout << "try to unlock package " << package << " in " << CmtSystem::pwd () << endl;
3973
3974  set_standard_macros ();
3975
3976  CmtLock::status status = CmtLock::unlock ();
3977}
3978
3979//----------------------------------------------------------
3980void Cmt::do_version (const ArgParser& /*ap*/)
3981{
3982  cout << CMTVERSION << endl;
3983}
3984
3985
3986
3987//----------------------------------------------------------
3988ActionType Cmt::get_action ()
3989{
3990  return (Me.m_action);
3991}
3992
3993/*
3994const CmtSystem::cmt_string_vector& Cmt::get_cmt_path ()
3995{
3996  return (Me.m_cmt_path);
3997}
3998
3999const CmtSystem::cmt_string_vector& Cmt::get_cmt_path_pwds ()
4000{
4001  return (Me.m_cmt_path_pwds);
4002}
4003
4004const CmtSystem::cmt_string_vector& Cmt::get_cmt_path_sources ()
4005{
4006  return (Me.m_cmt_path_sources);
4007}
4008*/
4009
4010const cmt_string& Cmt::get_cmt_home ()
4011{
4012  return (Me.m_cmt_home);
4013}
4014
4015const cmt_string& Cmt::get_cmt_user_context ()
4016{
4017  return (Me.m_cmt_user_context);
4018}
4019
4020const cmt_string& Cmt::get_cmt_version ()
4021{
4022  return (Me.m_cmt_version);
4023}
4024
4025const cmt_string& Cmt::get_current_dir ()
4026{
4027  return (Me.m_current_dir);
4028}
4029
4030const cmt_string& Cmt::get_current_package ()
4031{
4032  return (Me.m_current_package);
4033}
4034
4035const cmt_string& Cmt::get_current_cmtpath ()
4036{
4037  return (Me.m_current_cmtpath);
4038}
4039
4040const cmt_string& Cmt::get_current_offset ()
4041{
4042  return (Me.m_current_offset);
4043}
4044
4045AccessMode Cmt::get_current_access ()
4046{
4047  return (Me.m_current_access);
4048}
4049
4050CmtStructuringStyle Cmt::get_current_structuring_style ()
4051{
4052  return (Me.m_current_structuring_style);
4053}
4054
4055CmtDirStyle Cmt::get_current_style ()
4056{
4057  return (Me.m_current_style);
4058}
4059
4060const cmt_string& Cmt::get_current_version ()
4061{
4062  return (Me.m_current_version);
4063}
4064
4065const cmt_string& Cmt::get_current_target ()
4066{
4067  return (Me.m_current_target);
4068}
4069
4070bool Cmt::get_debug ()
4071{
4072  return (Me.m_debug);
4073}
4074
4075bool Cmt::get_quiet ()
4076{
4077  return (Me.m_quiet);
4078}
4079
4080bool Cmt::get_disable_warnings ()
4081{
4082  return (Me.m_disable_warnings);
4083}
4084
4085bool Cmt::get_warnings ()
4086{
4087  return (Me.m_warnings);
4088}
4089
4090bool Cmt::get_recursive ()
4091{
4092  return (Me.m_recursive);
4093}
4094
4095CmtScopeFilteringMode Cmt::get_scope_filtering_mode ()
4096{
4097  if (Me.m_scope_filtering_mode == default_filtering_mode)
4098    {
4099      return (block_private_uses);
4100    }
4101  else
4102    {
4103      return (Me.m_scope_filtering_mode);
4104    }
4105}
4106
4107//----------------------------------------------------------
4108bool Cmt::get_all_sets_done ()
4109{
4110  return (Me.m_all_sets_done);
4111}
4112
4113/**---------------------------------------------------------
4114  guess_current_project
4115
4116   if current directory is in one of the CMTPATHs, do nothing.
4117
4118  Otherwise, we want to guess the current project
4119
4120  move up in directories until cmt/project.cmt is found
4121
4122  for (;;)
4123  {
4124    if test -f ./cmt/project.cmt
4125      ok:
4126        this directory should become the first entry of the CMTPATH
4127        break
4128
4129    if (at top) break;
4130
4131    move up
4132  }
4133  */
4134void Cmt::guess_current_project ()
4135{
4136  Log;
4137
4138  log << "guess_current_project" << log_endl;
4139
4140  if (Project::find_in_cmt_paths (Me.m_current_dir) == "")
4141    {
4142      cmt_string project_file = "cmt";
4143      project_file += CmtSystem::file_separator ();
4144      project_file += Project::get_project_file_name ();
4145
4146      cmt_string pwd;
4147
4148      for (;;)
4149        {
4150          pwd = CmtSystem::pwd ();
4151          if (CmtSystem::test_file (project_file))
4152            {
4153              //this directory should become the first entry of the CMTPATH
4154
4155              IProjectFactory& factory = ProjectFactory::instance ();
4156              factory.create_project ("", pwd, "CurrentProject", 0);
4157
4158              break;
4159            }
4160
4161          log << "pwd=" << CmtSystem::pwd () << log_endl;
4162         
4163          if (!CmtSystem::cd (".."))
4164            {
4165              break;
4166            }
4167          if (CmtSystem::pwd () == pwd)
4168            {
4169              break;
4170            }
4171        }
4172      CmtSystem::cd (Me.m_current_dir);
4173    }
4174
4175  //cmt_string buffer = "path CMTPATH \n";
4176  cmt_string buffer;
4177  Project::fill_cmtpaths (buffer);
4178  //cerr << "buffer = " << buffer << endl;
4179  Use& use = Use::current();
4180  bool save_quiet = Me.m_quiet;
4181  Me.m_quiet = true;
4182  SyntaxParser::parse_requirements_text (buffer, "", &use);
4183  Me.m_quiet = save_quiet;
4184
4185  Me.m_autoconfigure_cmtpath = true;
4186}
4187
4188//----------------------------------------------------------
4189const cmt_string& Cmt::filter_dir (const cmt_string& dir)
4190{
4191  static cmt_string newdir;
4192
4193  CmtSystem::compress_path (dir, newdir);
4194
4195  return (newdir);
4196}
4197
4198//----------------------------------------------------------
4199static void dos_script_prefix (FILE* f, 
4200                               const cmt_string& cmt_root, 
4201                               const cmt_string& package, 
4202                               const cmt_string& version, 
4203                               const cmt_string& path, 
4204                               const cmt_string& action, 
4205                               const cmt_string& option = "")
4206{
4207  cmt_string no_device = path;
4208
4209  if (CmtSystem::absolute_path (path)) 
4210    {
4211      if (path[1] == ':')
4212        {
4213          no_device = path.substr (2);
4214        }
4215    }
4216
4217  if (package == "cmt_standalone")
4218    {
4219      no_device = "";
4220    }
4221  else
4222    {
4223      no_device = "..\\..\\..";
4224      if (Cmt::get_current_style () == no_version_style)
4225        {
4226          no_device = "..\\..";
4227        }
4228    }
4229
4230
4231  fprintf (f, "@echo off\n");
4232  fprintf (f, "if NOT DEFINED CMTROOT set CMTROOT=%s& set PATH=%%CMTROOT%%\\%%CMTBIN%%;%%PATH%%& set CMTBIN=VisualC& if not defined CMTCONFIG set CMTCONFIG=%%CMTBIN%%\n", cmt_root.c_str ());
4233  fprintf (f, "\n");
4234  fprintf (f, "set cmttempfile=\"%%TEMP%%\\tmpsetup.bat\"\n");
4235  fprintf (f, "%%CMTROOT%%\\%%CMTBIN%%\\cmt.exe %s -bat "
4236           " -pack=%s -version=%s -path=\"%%~d0%%~p0%s\" "
4237           " %s "
4238           "%%1 %%2 %%3 %%4 %%5 %%6 %%7 %%8 %%9 >%%cmttempfile%%\n",
4239           action.c_str (),
4240           package.c_str (),
4241           version.c_str (),
4242           no_device.c_str (),
4243           option.c_str ());
4244  fprintf (f, "if exist %%cmttempfile%% call %%cmttempfile%%\n");
4245  fprintf (f, "if exist %%cmttempfile%% del %%cmttempfile%%\n");
4246  fprintf (f, "set cmttempfile=\n");
4247}
4248
4249//----------------------------------------------------------
4250void Cmt::install_cleanup_scripts ()
4251{
4252#ifdef WIN32
4253  static const int modes = 1;
4254  static const cmt_string suffix[1]   = {"bat"};
4255  static const PrintMode  mode[1]     = {Bat};
4256#else
4257  static const int modes = 2;
4258  static const cmt_string suffix[2]   = {"csh", "sh"};
4259  static const PrintMode  mode[2]     = {Csh, Sh};
4260#endif
4261
4262  cout << "Creating cleanup scripts." << endl;
4263
4264  cmt_string temp;
4265  int i;
4266
4267  cmt_string version = Me.m_current_version;
4268  if (version == "v*") version = "";
4269
4270  for (i = 0; i < modes; i++)
4271    {
4272      cmt_string file_name = "cleanup";
4273      file_name += ".";
4274      file_name += suffix[i];
4275      file_name += ".";
4276      file_name += "new";
4277
4278      FILE* f = fopen (file_name.c_str (), "wb");
4279      if (f != NULL)
4280        {
4281          if (mode[i] == Csh)
4282            {
4283              fprintf (f, "if ( $?CMTROOT == 0 ) then\n");
4284              fprintf (f, "  setenv CMTROOT %s\n", Me.m_cmt_root.c_str ());
4285              fprintf (f, "endif\n");
4286              fprintf (f, "source ${CMTROOT}/mgr/setup.csh\n");
4287              fprintf (f, "set tempfile=`${CMTROOT}/mgr/cmt -quiet build temporary_name`\n");
4288              fprintf (f, "if $status != 0 then\n  set tempfile=/tmp/cmt.$$\nendif\n");
4289              fprintf (f, "${CMTROOT}/mgr/cmt cleanup -%s "
4290                       "-pack=%s -version=%s -path=%s $* >${tempfile}; "
4291                       "source ${tempfile}\n",
4292                       suffix[i].c_str (),
4293                       Me.m_current_package.c_str (),
4294                       version.c_str (),
4295                       Me.m_current_path.c_str ());
4296              fprintf (f, "/bin/rm -f ${tempfile}\n");
4297            }
4298          else if (mode[i] == Sh)
4299            {
4300              fprintf (f, "if test \"${CMTROOT}\" = \"\"; then\n");
4301              fprintf (f, "  CMTROOT=%s; export CMTROOT\n", Me.m_cmt_root.c_str ());
4302              fprintf (f, "fi\n");
4303              fprintf (f, ". ${CMTROOT}/mgr/setup.sh\n");
4304              fprintf (f, "tempfile=`${CMTROOT}/mgr/cmt -quiet build temporary_name`\n");
4305              fprintf (f, "if test ! $? = 0 ; then tempfile=/tmp/cmt.$$; fi\n");
4306              fprintf (f, "${CMTROOT}/mgr/cmt cleanup -%s "
4307                       "-pack=%s -version=%s -path=%s $* >${tempfile}; "
4308                       ". ${tempfile}\n",
4309                       suffix[i].c_str (),
4310                       Me.m_current_package.c_str (),
4311                       version.c_str (),
4312                       Me.m_current_path.c_str ());
4313              fprintf (f, "/bin/rm -f ${tempfile}\n");
4314            }
4315          else if (mode[i] == Bat)
4316            {
4317              dos_script_prefix (f, Me.m_cmt_root, 
4318                                 Me.m_current_package, version, Me.m_current_path,
4319                                 "cleanup");
4320            }
4321
4322          fprintf (f, "\n");
4323
4324          fclose (f);
4325
4326          cmt_string old_file_name = "cleanup";
4327          old_file_name += ".";
4328          old_file_name += suffix[i];
4329
4330          CmtSystem::compare_and_update_files (file_name, old_file_name);
4331        }
4332    }
4333}
4334
4335//----------------------------------------------------------
4336void Cmt::install_setup_scripts ()
4337{
4338#ifdef WIN32
4339  static const int modes = 1;
4340  static const cmt_string suffix[1]   = {"bat"};
4341  static const PrintMode  mode[1]     = {Bat};
4342#else
4343  static const int modes = 2;
4344  static const cmt_string suffix[2]   = {"csh", "sh"};
4345  static const PrintMode  mode[2]     = {Csh, Sh};
4346#endif
4347
4348  cout << "Creating setup scripts." << endl;
4349
4350  Use& current_use = Use::current ();
4351 
4352  cmt_string no_cleanup_opt;
4353
4354  if (current_use.get_strategy ("SetupCleanup"))
4355    {
4356      no_cleanup_opt = " -no_cleanup";
4357    }
4358
4359  cmt_string temp;
4360  int i;
4361
4362  cmt_string version = Me.m_current_version;
4363  if (version == "v*") version = "";
4364
4365  for (i = 0; i < modes; i++)
4366    {
4367      cmt_string file_name = "setup";
4368      file_name += ".";
4369      file_name += suffix[i];
4370      file_name += ".";
4371      file_name += "new";
4372
4373      FILE* f = fopen (file_name.c_str (), "wb");
4374      if (f != NULL)
4375        {
4376          if (mode[i] == Csh)
4377            {
4378              fprintf (f, "# echo \"Setting %s %s in %s\"\n",
4379                       Me.m_current_package.c_str (),
4380                       version.c_str (),
4381                       Me.m_current_path.c_str ());
4382              fprintf (f, "\n");
4383
4384              fprintf (f, "if ( $?CMTROOT == 0 ) then\n");
4385              fprintf (f, "  setenv CMTROOT %s\n", Me.m_cmt_root.c_str ());
4386              fprintf (f, "endif\n");
4387              fprintf (f, "source ${CMTROOT}/mgr/setup.csh\n");
4388              fprintf (f, "\n");
4389              fprintf (f, "set tempfile=`${CMTROOT}/mgr/cmt -quiet build temporary_name`\n");
4390              fprintf (f, "if $status != 0 then\n  set tempfile=/tmp/cmt.$$\nendif\n");
4391              fprintf (f, "${CMTROOT}/mgr/cmt setup -%s "
4392                       "-pack=%s -version=%s -path=%s %s $* >${tempfile}; "
4393                       "source ${tempfile}\n",
4394                       suffix[i].c_str (),
4395                       Me.m_current_package.c_str (),
4396                       version.c_str (),
4397                       Me.m_current_path.c_str (),
4398                       no_cleanup_opt.c_str ());
4399              fprintf (f, "/bin/rm -f ${tempfile}\n");
4400            }
4401          else if (mode[i] == Sh)
4402            {
4403              fprintf (f, "# echo \"Setting %s %s in %s\"\n",
4404                       Me.m_current_package.c_str (),
4405                       version.c_str (),
4406                       Me.m_current_path.c_str ());
4407              fprintf (f, "\n");
4408
4409              fprintf (f, "if test \"${CMTROOT}\" = \"\"; then\n");
4410              fprintf (f, "  CMTROOT=%s; export CMTROOT\n", Me.m_cmt_root.c_str ());
4411              fprintf (f, "fi\n");
4412              fprintf (f, ". ${CMTROOT}/mgr/setup.sh\n");
4413              fprintf (f, "\n");
4414              fprintf (f, "tempfile=`${CMTROOT}/mgr/cmt -quiet build temporary_name`\n");
4415              fprintf (f, "if test ! $? = 0 ; then tempfile=/tmp/cmt.$$; fi\n");
4416              fprintf (f, "${CMTROOT}/mgr/cmt setup -%s "
4417                       "-pack=%s -version=%s -path=%s %s $* >${tempfile}; "
4418                       ". ${tempfile}\n",
4419                       suffix[i].c_str (),
4420                       Me.m_current_package.c_str (),
4421                       version.c_str (),
4422                       Me.m_current_path.c_str (),
4423                       no_cleanup_opt.c_str ());
4424              fprintf (f, "/bin/rm -f ${tempfile}\n");
4425            }
4426          else if (mode[i] == Bat)
4427            {
4428              fprintf (f, "rem Setting %s %s in %%~d0%%~p0\n",
4429                       Me.m_current_package.c_str (),
4430                       version.c_str ());
4431              dos_script_prefix (f, Me.m_cmt_root, 
4432                                 Me.m_current_package, version, Me.m_current_path,
4433                                 "setup", no_cleanup_opt);
4434            }
4435
4436          fprintf (f, "\n");
4437
4438          fclose (f);
4439
4440          cmt_string old_file_name = "setup";
4441          old_file_name += ".";
4442          old_file_name += suffix[i];
4443
4444          CmtSystem::compare_and_update_files (file_name, old_file_name);
4445        }
4446    }
4447}
4448
4449//----------------------------------------------------------
4450void Cmt::install_test_cleanup_scripts ()
4451{
4452#ifdef WIN32
4453  static const int modes = 1;
4454  static const cmt_string suffix[1]   = {"bat"};
4455  static const PrintMode  mode[1]     = {Bat};
4456#else
4457  static const int modes = 2;
4458  static const cmt_string suffix[2]   = {"csh", "sh"};
4459  static const PrintMode  mode[2]     = {Csh, Sh};
4460#endif
4461
4462  cout << "Creating cleanup scripts." << endl;
4463
4464  cmt_string temp;
4465  int i;
4466
4467  cmt_string version = Me.m_current_version;
4468  if (version == "v*") version = "";
4469
4470  for (i = 0; i < modes; i++)
4471    {
4472      cmt_string file_name = "cleanup";
4473      file_name += ".";
4474      file_name += suffix[i];
4475      file_name += ".";
4476      file_name += "new";
4477
4478      FILE* f = fopen (file_name.c_str (), "wb");
4479      if (f != NULL)
4480        {
4481          if (mode[i] == Csh)
4482            {
4483              fprintf (f, "if ( $?CMTROOT == 0 ) then\n");
4484              fprintf (f, "  setenv CMTROOT %s\n", Me.m_cmt_root.c_str ());
4485              fprintf (f, "endif\n");
4486              fprintf (f, "source ${CMTROOT}/mgr/setup.csh\n");
4487              fprintf (f, "set tempfile=`${CMTROOT}/mgr/cmt -quiet build temporary_name`\n");
4488              fprintf (f, "if $status != 0 then\n  set tempfile=/tmp/cmt.$$\nendif\n");
4489              fprintf (f, "${CMTROOT}/mgr/cmt cleanup -%s -pack=cmt_standalone -path=%s $* >${tempfile}; "
4490                       "source ${tempfile}\n",
4491                       suffix[i].c_str (),
4492                       Me.m_current_path.c_str ());
4493              fprintf (f, "/bin/rm -f ${tempfile}\n");
4494            }
4495          else if (mode[i] == Sh)
4496            {
4497              fprintf (f, "if test \"${CMTROOT}\" = \"\"; then\n");
4498              fprintf (f, "  CMTROOT=%s; export CMTROOT\n", Me.m_cmt_root.c_str ());
4499              fprintf (f, "fi\n");
4500              fprintf (f, ". ${CMTROOT}/mgr/setup.sh\n");
4501              fprintf (f, "tempfile=`${CMTROOT}/mgr/cmt -quiet build temporary_name`\n");
4502              fprintf (f, "if test ! $? = 0 ; then tempfile=/tmp/cmt.$$; fi\n");
4503              fprintf (f, "${CMTROOT}/mgr/cmt cleanup -%s -pack=cmt_standalone -path=%s $* >${tempfile}; "
4504                       ". ${tempfile}\n",
4505                       suffix[i].c_str (),
4506                       Me.m_current_path.c_str ());
4507              fprintf (f, "/bin/rm -f ${tempfile}\n");
4508            }
4509          else
4510            {
4511              dos_script_prefix (f, Me.m_cmt_root, 
4512                                 "cmt_standalone", "", Me.m_current_path, 
4513                                 "cleanup");
4514            }
4515
4516          fprintf (f, "\n");
4517
4518          fclose (f);
4519
4520          cmt_string old_file_name = "cleanup";
4521          old_file_name += ".";
4522          old_file_name += suffix[i];
4523
4524          CmtSystem::compare_and_update_files (file_name, old_file_name);
4525        }
4526    }
4527}
4528
4529//----------------------------------------------------------
4530void Cmt::install_native_version_file ()
4531{   
4532  Use& current_use        = Use::current ();
4533  cmt_string package_name = current_use.get_package_name();
4534  cmt_string macro_name   = package_name + "_native_version";
4535  Symbol* macro           = Symbol::find (macro_name);
4536  if (macro != 0)
4537  {
4538      cmt_string value = macro->resolve_macro_value ();
4539      if (value != "")
4540      {
4541        cout << "Creating native_version file." << endl;   
4542        FILE* f          = fopen ("new.native_version.cmt", "wb");
4543        if (f != NULL)
4544        {
4545            fprintf (f, "%s\n", value.c_str ());
4546        }     
4547        //cout<<value <<endl;
4548        fclose (f);
4549
4550        CmtSystem::compare_and_update_files ("new.native_version.cmt", "native_version.cmt");
4551      } 
4552  }   
4553}
4554//----------------------------------------------------------
4555void Cmt::install_test_setup_scripts ()
4556{
4557#ifdef WIN32
4558  static const int modes = 1;
4559  static const cmt_string suffix[1]   = {"bat"};
4560  static const PrintMode  mode[1]     = {Bat};
4561#else
4562  static const int modes = 2;
4563  static const cmt_string suffix[2]   = {"csh", "sh"};
4564  static const PrintMode  mode[2]     = {Csh, Sh};
4565#endif
4566
4567  cout << "Creating setup scripts." << endl;
4568
4569  Use& current_use = Use::current ();
4570
4571  cmt_string no_cleanup_opt;
4572
4573  if (current_use.get_strategy ("SetupCleanup"))
4574    {
4575      no_cleanup_opt = " -no_cleanup";
4576    }
4577
4578  cmt_string temp;
4579  int i;
4580
4581  for (i = 0; i < modes; i++)
4582    {
4583      cmt_string file_name = "setup";
4584      file_name += ".";
4585      file_name += suffix[i];
4586      file_name += ".";
4587      file_name += "new";
4588
4589      FILE* f = fopen (file_name.c_str (), "wb");
4590      if (f != NULL)
4591        {
4592          if (mode[i] == Csh)
4593            {
4594              fprintf (f, "# echo \"Setting standalone package\"\n");
4595              fprintf (f, "\n");
4596
4597              fprintf (f, "if ( $?CMTROOT == 0 ) then\n");
4598              fprintf (f, "  setenv CMTROOT %s\n", Me.m_cmt_root.c_str ());
4599              fprintf (f, "endif\n");
4600              fprintf (f, "source ${CMTROOT}/mgr/setup.csh\n");
4601              fprintf (f, "set tempfile=`${CMTROOT}/mgr/cmt -quiet build temporary_name`\n");
4602              fprintf (f, "if $status != 0 then\n  set tempfile=/tmp/cmt.$$\nendif\n");
4603              fprintf (f, "${CMTROOT}/mgr/cmt setup -%s -pack=cmt_standalone -path=%s %s $* >${tempfile}; "
4604                       "source ${tempfile}\n",
4605                       suffix[i].c_str (),
4606                       Me.m_current_path.c_str (),
4607                       no_cleanup_opt.c_str ());
4608              fprintf (f, "/bin/rm -f ${tempfile}\n");
4609            }
4610          else if (mode[i] == Sh)
4611            {
4612              fprintf (f, "# echo \"Setting standalone package\"\n");
4613              fprintf (f, "\n");
4614
4615              fprintf (f, "if test \"${CMTROOT}\" = \"\"; then\n");
4616              fprintf (f, "  CMTROOT=%s; export CMTROOT\n", Me.m_cmt_root.c_str ());
4617              fprintf (f, "fi\n");
4618              fprintf (f, ". ${CMTROOT}/mgr/setup.sh\n");
4619              fprintf (f, "\n");
4620              fprintf (f, "tempfile=`${CMTROOT}/mgr/cmt -quiet build temporary_name`\n");
4621              fprintf (f, "if test ! $? = 0 ; then tempfile=/tmp/cmt.$$; fi\n");
4622              fprintf (f, "${CMTROOT}/mgr/cmt setup -%s -pack=cmt_standalone -path=%s %s $* >${tempfile}; "
4623                       ". ${tempfile}\n",
4624                       suffix[i].c_str (),
4625                       Me.m_current_path.c_str (),
4626                       no_cleanup_opt.c_str ());
4627              fprintf (f, "/bin/rm -f ${tempfile}\n");
4628            }
4629          else
4630            {
4631              fprintf (f, "rem Setting standalone package\n");
4632              dos_script_prefix (f, Me.m_cmt_root, 
4633                                 "cmt_standalone", "", Me.m_current_path, 
4634                                 "setup", no_cleanup_opt);
4635            }
4636
4637          fprintf (f, "\n");
4638
4639          fclose (f);
4640
4641          cmt_string old_file_name = "setup";
4642          old_file_name += ".";
4643          old_file_name += suffix[i];
4644
4645          CmtSystem::compare_and_update_files (file_name, old_file_name);
4646        }
4647    }
4648}
4649
4650/**
4651 *    load is only called from the Windows GUI which pretends to access directly
4652 *   the internal data model.
4653 *    This is considered to be rather unsafe, and should be replaced by query functions.
4654 */
4655bool Cmt::load (const cmt_string& path,
4656                const cmt_string& package,
4657                const cmt_string& version,
4658                const cmt_string& tag_name)
4659{
4660  clear ();
4661  configure ();
4662
4663  Me.m_action  = action_load;
4664  Me.m_recursive = true;
4665
4666  if (((package != "") && (version != "")) || (Me.m_current_package == ""))
4667    {
4668      //
4669      //  Here we want to connect to a new package, or to the current package
4670      //  but with another tag.
4671      //
4672      //   the 'package' argument may include a directory offset. Thus 'path'
4673      //  is only expected to hold the base directory.
4674      //
4675      cmt_string offset;
4676      cmt_string package_name;
4677     
4678      CmtSystem::dirname (package, offset);
4679      CmtSystem::basename (package, package_name);
4680     
4681      if (offset != "")
4682        {
4683          Me.m_current_path = path;
4684          Me.m_current_path += CmtSystem::file_separator ();
4685          Me.m_current_path += offset;
4686        }
4687      else
4688        {
4689          Me.m_current_path = path;
4690        }
4691     
4692      Me.m_current_package = package_name;
4693      Me.m_current_version = version;
4694    }
4695
4696  if (tag_name != "")
4697    {
4698      Tag* tag;
4699
4700      Tag::unmark_all ();
4701      configure_version_tag ();
4702      configure_site_tag (0);
4703      configure_uname_tag ();
4704      configure_hosttype_tag ();
4705
4706      Me.m_current_tag = tag_name;
4707
4708      //if (!Me.m_quiet) cerr << "load1> current_tag=" << Me.m_current_tag << endl;
4709
4710      tag = Tag::add (tag_name, PriorityTag, "load", 0);
4711      tag->mark ();
4712    }
4713
4714  /*
4715    Set to developer mode if positioned into the package
4716    (which is detected since we were able to retreive the
4717    Version, Package and Path)
4718  */
4719
4720  if ((Me.m_current_path == "") ||
4721      (Me.m_current_package == "") ||
4722      (Me.m_current_version == ""))
4723    {
4724      Me.m_current_access = UserMode;
4725    }
4726  else
4727    {
4728      Me.m_current_access = DeveloperMode;
4729    }
4730
4731  use_cmt ();
4732
4733  cmt_string dir;
4734
4735  /*
4736    Try to access the package.
4737  */
4738
4739  if (Me.m_current_path != "")
4740    {
4741      dir = Me.m_current_path;
4742    }
4743  else
4744    {
4745      dir = Me.m_default_path;
4746    }
4747
4748  if (!CmtSystem::cd (Me.m_current_path))
4749    {
4750      if (!Me.m_quiet)
4751        {
4752          cerr << "#CMT> Cannot reach the directory " <<
4753            Me.m_current_path << endl;
4754        }
4755      CmtError::set (CmtError::package_not_found, "Load> Cannot reach the path directory");
4756      CmtSystem::cd (Me.m_current_dir);
4757
4758      return (false);
4759    }
4760
4761  dir += CmtSystem::file_separator ();
4762  dir += Me.m_current_package;
4763
4764  if (!CmtSystem::cd (Me.m_current_package))
4765    {
4766      if (!Me.m_quiet)
4767        {
4768          cerr << "#CMT::load> Cannot reach the package " <<
4769            Me.m_current_package << endl;
4770        }
4771      CmtError::set (CmtError::package_not_found, "Load> Cannot reach the package directory");
4772      CmtSystem::cd (Me.m_current_dir);
4773
4774      return (false);
4775    }
4776
4777  dir += CmtSystem::file_separator ();
4778  dir += Me.m_current_version;
4779
4780  Me.m_current_style = none_style;
4781
4782  if (!CmtSystem::cd (Me.m_current_version))
4783    {
4784      if (!CmtSystem::test_directory ("cmt"))
4785        {
4786          if (!Me.m_quiet)
4787            {
4788              cerr << "#CMT> Cannot reach the version " <<
4789                Me.m_current_version << endl;
4790            }
4791          CmtError::set (CmtError::package_not_found, "Load> Cannot reach the version directory");
4792          CmtSystem::cd (Me.m_current_dir);
4793
4794          return (false);
4795        }
4796      else
4797        {
4798          Me.m_current_style = no_version_style;
4799        }
4800    }
4801
4802  if (CmtSystem::cd ("cmt"))
4803    {
4804      dir += CmtSystem::file_separator ();
4805      dir += "cmt";
4806      if (Me.m_current_style == none_style) Me.m_current_style = cmt_style;
4807    }
4808  else
4809    {
4810      /*
4811        if (!Me.m_quiet)
4812        {
4813        cerr << "Cannot reach the cmt branch" << endl;
4814        }
4815      */
4816
4817      if (CmtSystem::cd ("mgr"))
4818        {
4819          dir += CmtSystem::file_separator ();
4820          dir += "mgr";
4821          if (Me.m_current_style == none_style) Me.m_current_style = mgr_style;
4822        }
4823      else
4824        {
4825          if (!Me.m_quiet)
4826            {
4827              cerr << "#CMT> Cannot reach the mgr branch" << endl;
4828            }
4829
4830          CmtError::set (CmtError::package_not_found,
4831                         "Load> Cannot reach the mgr/cmt directory");
4832          CmtSystem::cd (Me.m_current_dir);
4833
4834          return (false);
4835        }
4836    }
4837
4838  /*
4839    Check Tag is always set up
4840  */
4841
4842  if (Me.m_current_tag == "")
4843    {
4844      char* env;
4845
4846      env = getenv (Me.m_current_config.c_str ());
4847      if (env != 0)
4848        {
4849          Tag* tag;
4850
4851          tag = Tag::add (env, PriorityConfig, "load", 0);
4852          tag->mark ();
4853          Me.m_current_tag = env;
4854
4855          //if (!Me.m_quiet) cerr << "load2> current_tag=" << Me.m_current_tag << endl;
4856
4857        }
4858      else
4859        {
4860          Me.m_current_tag = Me.m_cmt_config;
4861
4862          //if (!Me.m_quiet) cerr << "load3> current_tag=" << Me.m_current_tag << endl;
4863
4864        }
4865    }
4866
4867  if (Me.m_debug)
4868    {
4869      cout << "pwd = " << CmtSystem::pwd () << endl;
4870    }
4871
4872  configure_current_dir ();
4873  build_prefix (Me.m_current_package, Me.m_current_prefix);
4874  build_config (Me.m_current_prefix, Me.m_current_config);
4875
4876  Use* use = &(Use::current());
4877  use->path    = Me.m_current_path;
4878  use->set_package_name (Me.m_current_package);
4879  use->version = Me.m_current_version;
4880  use->prefix  = Me.m_current_prefix;
4881  use->done    = false;
4882  use->style   = Me.m_current_style;
4883
4884  /*
4885    Work on the requirements file.
4886  */
4887
4888  dir += CmtSystem::file_separator ();
4889  dir += "requirements";
4890  SyntaxParser::parse_requirements (dir, use);
4891
4892  if (CmtError::has_pending_error ()) return (false);
4893
4894    /**
4895     * See reach_current_package for an explanation of this call
4896     */
4897  Pattern::apply_all_globals ();
4898
4899  /*
4900    Select all possible tags
4901  */
4902
4903  Tag::restore_tree ();
4904
4905  return (true);
4906}
4907
4908//----------------------------------------------------------
4909bool Cmt::need_prototypes ()
4910{
4911  Use& current_use = Use::current ();
4912
4913  if (current_use.get_strategy ("BuildPrototypes")) return (true);
4914  else return (false);
4915}
4916
4917//----------------------------------------------------------
4918void Cmt::parse_arguments (ArgParser& ap)
4919{
4920  /*
4921    Decoding arguments.
4922
4923    While decoding all arguments, no requirements analysis should
4924    occur. Every new option, or parameter should be saved and
4925    used later at actual analysis time.
4926  */
4927
4928  Me.m_action = action_none;
4929
4930  restore_all_tags (0);
4931
4932#ifdef WIN32
4933  Me.m_build_nmake = true;
4934#endif
4935
4936  ap.parse ();
4937}
4938
4939//----------------------------------------------------------
4940int Cmt::parser (const cmt_string& command_line)
4941{
4942  CmtSystem::cmt_string_vector v;
4943
4944  CmtSystem::split (command_line, " \t", v);
4945
4946  int argc = v.size ();
4947
4948  char** argv = (char**) malloc ((argc + 1) * sizeof (char*));
4949
4950  int i;
4951  for (i = 0; i < argc; i++)
4952    {
4953      argv[i] = (char*) v[i].c_str ();
4954    }
4955  argv[argc] = 0;
4956
4957  int status = parser (argc, argv);
4958
4959  free (argv);
4960
4961  return (status);
4962}
4963
4964//----------------------------------------------------------
4965int Cmt::parser (int argc, char* argv[])
4966{
4967  ArgParser ap (Me);
4968 
4969  ap.argc = argc;
4970  ap.argv = argv;
4971
4972  if (argc <= 1)
4973    {
4974      do_help (ap);
4975      exit (0);
4976    }
4977
4978
4979  clear ();
4980  configure ();
4981
4982  CmtError::clear ();
4983
4984  /*
4985    Set private if positioned inside the package
4986    (which is detected since we were able to retreive the
4987    Version, Package and Path)
4988  */
4989
4990  if ((Me.m_current_path.size () == 0) ||
4991      (Me.m_current_package.size () == 0) ||
4992      (Me.m_current_version.size () == 0))
4993    {
4994      Me.m_current_access = UserMode;
4995    }
4996  else
4997    {
4998      Me.m_current_access = DeveloperMode;
4999    }
5000 
5001  parse_arguments (ap);
5002 
5003  if (Me.m_debug)
5004    {
5005      cout << "After parse_argument> pack=" << Me.m_current_package
5006           << " Me.m_current_tag=" << Me.m_current_tag
5007           << " cwd=" << CmtSystem::pwd () 
5008           << " mode=" << Me.m_current_access
5009           << endl;
5010    }
5011
5012  if (Me.m_configure_error != "")
5013    {
5014      if (!Me.m_quiet) cerr << "#CMT> Error: " << Me.m_configure_error << endl;
5015      return (CmtError::execution_error);
5016    }
5017
5018  if (CmtError::has_pending_error ())
5019    {
5020      int code = CmtError::get_last_error_code ();
5021      if (!Me.m_quiet) CmtError::print ();
5022      clear ();
5023
5024      return (code);
5025    }
5026
5027  /*
5028    Now actual requirements analysis can take place.
5029
5030    Extra lines or files are analysed first.
5031  */
5032
5033  if (strlen (ap.extra_file.c_str ()) > 0) SyntaxParser::parse_requirements (ap.extra_file, (Use*) 0);
5034  if (strlen (ap.extra_line.c_str ()) > 0) SyntaxParser::parse_requirements_line (ap.extra_line, (Use*) 0);
5035
5036  //
5037  //  For some of the actions, the CMT package must be automatically
5038  //  included
5039  //
5040
5041  if (Me.m_debug) cout << "parser1> current_tag=" << Me.m_current_tag << endl;
5042
5043  if (ap.help_action == action_help)
5044    {
5045      do_help (ap);
5046      return (0);
5047    }
5048
5049  switch (Me.m_action)
5050    {
5051      // case action_none :
5052    case action_awk :
5053    case action_broadcast :
5054    case action_build_constituent_makefile :
5055    case action_build_constituents_makefile :
5056    case action_build_dependencies :
5057    case action_build_library_links :
5058    case action_build_make_setup :
5059    case action_build_msdev :
5060    case action_build_CMT_pacman :
5061    case action_build_vsnet :     
5062    case action_build_os9_makefile :
5063      // case action_build_prototype :
5064    case action_build_readme :
5065    case action_build_tag_makefile :
5066      // case action_build_temporary_name :
5067    case action_build_triggers :
5068    case action_build_windefs :
5069    case action_check_configuration :
5070      // case action_check_files :
5071      // case action_check_version :
5072    case action_checkout :
5073    case action_cleanup :
5074    case action_config :
5075    case action_create :
5076      // case action_create_project :
5077    case action_cvsbranches :
5078    case action_cvssubpackages :
5079    case action_cvssubprojects :
5080    case action_cvstags :
5081    case action_do :
5082    case action_expand_model :
5083    case action_filter :
5084      // case action_help :
5085    case action_load :
5086    case action_lock :
5087    case action_relocate:
5088    case action_remove :
5089    case action_remove_library_links :
5090    case action_run :
5091    case action_run_sequence :
5092    case action_set_version :
5093    case action_set_versions :
5094    case action_setup :
5095    case action_show_action :
5096    case action_show_action_names :
5097    case action_show_action_value :
5098    case action_show_actions :
5099    case action_show_all_tags :
5100    case action_show_applied_patterns :
5101      // case action_show_author :
5102      // case action_show_branches :
5103      // case action_show_clients :
5104    case action_show_cmtpath_patterns :
5105    case action_show_constituent :
5106    case action_show_constituent_names :
5107    case action_show_constituents :
5108    case action_show_cycles :
5109    case action_show_fragment :
5110    case action_show_fragments :
5111    case action_show_groups :
5112    case action_show_include_dirs :
5113    case action_show_language :
5114    case action_show_languages :
5115    case action_show_macro :
5116    case action_show_macro_names :
5117    case action_show_macro_value :
5118    case action_show_macros :
5119      // case action_show_manager :
5120    case action_show_packages :
5121    case action_show_path :
5122    case action_show_pattern :
5123    case action_show_pattern_names :
5124    case action_show_patterns :
5125    case action_show_projects :
5126      // case action_show_pwd :
5127    case action_show_setup :
5128    case action_show_set :
5129    case action_show_set_names :
5130    case action_show_set_value :
5131    case action_show_sets :
5132    case action_show_strategies :
5133    case action_show_tags :
5134    case action_show_use_paths :
5135    case action_show_uses :
5136    case action_show_version :
5137      // case action_show_versions :
5138      // case action_system :
5139    case action_unlock :
5140    case action_version :
5141      use_cmt ();
5142        //
5143        // Now parse the requirements file stored in ${CMTHOME}
5144        //
5145     
5146      use_home_requirements ();
5147
5148      break;
5149    default:
5150      break;
5151    }
5152
5153  if (Me.m_debug) cout << "parser2> current_tag=" << Me.m_current_tag << endl;
5154
5155  //
5156  // Setting up recursive actions
5157  //
5158
5159  switch (Me.m_action)
5160    {
5161      // case action_none :
5162    case action_awk :
5163    case action_broadcast :
5164    case action_build_constituent_makefile :
5165    case action_build_constituents_makefile :
5166    case action_build_dependencies :
5167    case action_build_library_links :
5168    case action_build_make_setup :
5169    case action_build_msdev :
5170    case action_build_CMT_pacman :
5171    case action_build_vsnet :     
5172    case action_build_os9_makefile :
5173      // case action_build_prototype :
5174    case action_build_readme :
5175    case action_build_tag_makefile :
5176      // case action_build_temporary_name :
5177    case action_build_triggers :
5178    case action_build_windefs :
5179    case action_check_configuration :
5180      // case action_check_files :
5181      // case action_check_version :
5182      // case action_checkout :
5183    case action_cleanup :
5184    case action_config :
5185      // case action_create :
5186      // case action_create_project :
5187      // case action_cvsbranches :
5188      // case action_cvssubpackages :
5189      // case action_cvssubprojects :
5190      // case action_cvstags :
5191    case action_do :
5192    case action_expand_model :
5193    case action_filter :
5194      // case action_help :
5195    case action_load :
5196      // case action_lock :
5197      // case action_remove :
5198    case action_relocate:
5199    case action_remove_library_links :
5200    case action_run :
5201    case action_run_sequence :
5202      // case action_set_version :
5203    case action_set_versions :
5204    case action_setup :
5205    case action_show_action :
5206    case action_show_action_names :
5207    case action_show_action_value :
5208    case action_show_actions :
5209    case action_show_all_tags :
5210    case action_show_applied_patterns :
5211      // case action_show_author :
5212      // case action_show_branches :
5213      // case action_show_clients :
5214    case action_show_cmtpath_patterns :
5215    case action_show_constituent :
5216    case action_show_constituent_names :
5217    case action_show_constituents :
5218    case action_show_cycles :
5219    case action_show_fragment :
5220    case action_show_fragments :
5221    case action_show_groups :
5222    case action_show_include_dirs :
5223    case action_show_language :
5224    case action_show_languages :
5225    case action_show_macro :
5226    case action_show_macro_names :
5227    case action_show_macro_value :
5228    case action_show_macros :
5229      // case action_show_manager :
5230    case action_show_packages :
5231    case action_show_path :
5232    case action_show_pattern :
5233    case action_show_pattern_names :
5234    case action_show_patterns :
5235    case action_show_projects :
5236      // case action_show_pwd :
5237    case action_show_setup :
5238    case action_show_set :
5239    case action_show_set_names :
5240    case action_show_set_value :
5241    case action_show_sets :
5242    case action_show_strategies :
5243    case action_show_tags :
5244    case action_show_use_paths :
5245    case action_show_uses :
5246      // case action_show_version :
5247      // case action_show_versions :
5248      // case action_system :
5249      // case action_unlock :
5250      // case action_version :
5251      Me.m_recursive = true;
5252      break;
5253    default:
5254      Me.m_recursive = false;
5255      break;
5256    }
5257
5258  //
5259  //  Actions for which the context of the package is checked,
5260  //  and the requirements file is analysed.
5261  //
5262
5263  switch (Me.m_action)
5264    {
5265    case action_none :
5266    case action_awk :
5267    case action_broadcast :
5268    case action_build_constituent_makefile :
5269    case action_build_constituents_makefile :
5270    case action_build_dependencies :
5271    case action_build_library_links :
5272    case action_build_make_setup :
5273    case action_build_msdev :
5274    case action_build_CMT_pacman :
5275    case action_build_vsnet :     
5276    case action_build_os9_makefile :
5277      // case action_build_prototype :
5278    case action_build_readme :
5279    case action_build_tag_makefile :
5280      // case action_build_temporary_name :
5281    case action_build_triggers :
5282    case action_build_windefs :
5283    case action_check_configuration :
5284      // case action_check_files :
5285      // case action_check_version :
5286      // case action_checkout :
5287    case action_cleanup :
5288    case action_config :
5289      // case action_create :
5290      // case action_create_project :
5291      // case action_cvsbranches :
5292      // case action_cvssubpackages :
5293      // case action_cvssubprojects :
5294      // case action_cvstags :
5295    case action_do :
5296    case action_expand_model :
5297    case action_filter :
5298      // case action_help :
5299    case action_load :
5300    case action_lock :
5301      // case action_remove :
5302    case action_relocate :
5303    case action_remove_library_links :
5304    case action_run :
5305      // case action_run_sequence :
5306      // case action_set_version :
5307    case action_set_versions :
5308    case action_setup :
5309    case action_show_action :
5310    case action_show_action_names :
5311    case action_show_action_value :
5312    case action_show_actions :
5313    case action_show_all_tags :
5314    case action_show_applied_patterns :
5315    case action_show_author :
5316    case action_show_branches :
5317      // case action_show_clients :
5318    case action_show_cmtpath_patterns :
5319    case action_show_constituent :
5320    case action_show_constituent_names :
5321    case action_show_constituents :
5322    case action_show_cycles :
5323    case action_show_fragment :
5324    case action_show_fragments :
5325    case action_show_groups :
5326    case action_show_include_dirs :
5327    case action_show_language :
5328    case action_show_languages :
5329    case action_show_macro :
5330    case action_show_macro_names :
5331    case action_show_macro_value :
5332    case action_show_macros :
5333    case action_show_manager :
5334    case action_show_packages :
5335    case action_show_path :
5336    case action_show_pattern :
5337    case action_show_pattern_names :
5338    case action_show_patterns :
5339    case action_show_projects :
5340    case action_show_project_author :
5341    case action_show_pwd :
5342    case action_show_setup :
5343    case action_show_set :
5344    case action_show_set_names :
5345    case action_show_set_value :
5346    case action_show_sets :
5347    case action_show_strategies :
5348    case action_show_tags :
5349    case action_show_use_paths :
5350    case action_show_uses :
5351    case action_show_version :
5352      // case action_show_versions :
5353      // case action_system :
5354    case action_unlock :
5355      // case action_version :
5356      {
5357        bool w = Me.m_warnings;
5358        Me.m_warnings = false;
5359        reach_current_package ();
5360        use_user_context_requirements ();
5361        Me.m_warnings = w;
5362      }
5363      break;
5364    default:
5365      break;
5366    }
5367
5368  if (Me.m_debug) cout << "parser3> current_tag=" << Me.m_current_tag << endl;
5369
5370  //
5371  // Perform some actions even if there is an error
5372  //
5373
5374  if (CmtError::has_pending_error ())
5375    {
5376      int code = CmtError::get_last_error_code ();
5377      if (!Me.m_quiet) CmtError::print ();
5378
5379      switch (Me.m_action)
5380        {
5381          // case action_none :
5382          // case action_awk :
5383          // case action_broadcast :
5384        case action_build_constituent_makefile :
5385        case action_build_constituents_makefile :
5386        case action_build_dependencies :
5387        case action_build_library_links :
5388        case action_build_make_setup :
5389        case action_build_msdev :
5390        case action_build_CMT_pacman :
5391        case action_build_vsnet :     
5392        case action_build_os9_makefile :
5393        case action_build_prototype :
5394        case action_build_readme :
5395        case action_build_tag_makefile :
5396          // case action_build_temporary_name :
5397        case action_build_triggers :
5398        case action_build_windefs :
5399        case action_check_configuration :
5400          // case action_check_files :
5401          // case action_check_version :
5402          // case action_checkout :
5403        case action_cleanup :
5404          // case action_config :
5405          // case action_create :
5406          // case action_create_project :
5407          // case action_cvsbranches :
5408          // case action_cvssubpackages :
5409          // case action_cvssubprojects :
5410          // case action_cvstags :
5411          // case action_do :
5412          // case action_expand_model :
5413          // case action_filter :
5414          // case action_help :
5415        case action_load :
5416        case action_lock :
5417        case action_relocate :
5418        case action_remove :
5419        case action_remove_library_links :
5420          // case action_run :
5421        case action_run_sequence :
5422          // case action_set_version :
5423          // case action_set_versions :
5424        case action_setup :
5425          // case action_show_action :
5426          // case action_show_action_names :
5427          // case action_show_action_value :
5428          // case action_show_actions :
5429          // case action_show_all_tags :
5430          // case action_show_applied_patterns :
5431          // case action_show_author :
5432          // case action_show_branches :
5433          // case action_show_clients :
5434          // case action_show_cmtpath_patterns :
5435          // case action_show_constituent :
5436          // case action_show_constituent_names :
5437          // case action_show_constituents :
5438          // case action_show_cycles :
5439          // case action_show_fragment :
5440          // case action_show_fragments :
5441          // case action_show_groups :
5442          // case action_show_include_dirs :
5443          // case action_show_language :
5444          // case action_show_languages :
5445          // case action_show_macro :
5446          // case action_show_macro_names :
5447          // case action_show_macro_value :
5448          // case action_show_macros :
5449          // case action_show_manager :
5450          // case action_show_packages :
5451          // case action_show_path :
5452          // case action_show_pattern :
5453          // case action_show_pattern_names :
5454          // case action_show_patterns :
5455          // case action_show_projects :
5456          // case action_show_pwd :
5457          // case action_show_setup :
5458          // case action_show_set :
5459          // case action_show_set_names :
5460          // case action_show_set_value :
5461          // case action_show_sets :
5462          // case action_show_strategies :
5463          // case action_show_tags :
5464          // case action_show_use_paths :
5465          // case action_show_uses :
5466          // case action_show_version :
5467          // case action_show_versions :
5468          // case action_system :
5469        case action_unlock :
5470          // case action_version :
5471          clear ();
5472          return (code);
5473        default:
5474          CmtError::clear ();
5475          break;
5476        }
5477    }
5478
5479  //
5480  // Perform actions
5481  //
5482
5483  if (!Me.m_simulation)
5484    {
5485      switch (Me.m_action)
5486        {
5487        case action_none :
5488          //CmtError::set (CmtError::syntax_error, "ParseArguments> ");
5489          break;
5490        case action_awk :
5491          do_awk (ap);
5492      break;
5493        case action_broadcast :
5494          do_broadcast (ap);
5495          break;
5496        case action_build_constituent_makefile :
5497          do_build_constituent_makefile (ap);
5498          break;
5499        case action_build_constituents_makefile :
5500          do_build_constituents_makefile (ap);
5501          break;
5502        case action_build_dependencies :
5503          do_build_dependencies (ap, argc, argv);
5504          break;
5505        case action_build_library_links :
5506          do_build_library_links (ap);
5507          break;
5508        case action_build_make_setup :
5509          do_build_make_setup (ap);
5510          break;
5511        case action_build_msdev :
5512          do_build_msdev (ap);
5513          break;
5514        case action_build_CMT_pacman :
5515          do_build_CMT_pacman (ap);
5516          break;
5517        case action_build_vsnet :     
5518          do_build_vsnet (ap);
5519          break;
5520        case action_build_os9_makefile :
5521          do_build_os9_makefile (ap);
5522          break;
5523        case action_build_prototype :
5524          do_build_prototype (ap);
5525          break;
5526        case action_build_readme :
5527          do_build_readme (ap);
5528          break;
5529        case action_build_tag_makefile :
5530          do_build_tag_makefile (ap);
5531          break;
5532        case action_build_temporary_name :
5533          do_build_temporary_name (ap);
5534          break;
5535        case action_build_triggers :
5536          do_build_triggers (ap);
5537          break;
5538        case action_build_windefs :
5539          do_build_windefs (ap);
5540          break;
5541        case action_check_configuration :
5542          do_check_configuration (ap);
5543          break;
5544        case action_check_files :
5545          do_check_files (ap);
5546          break;
5547        case action_check_version :
5548          do_check_version (ap);
5549          break;
5550        case action_checkout :
5551          do_checkout (ap);
5552          break;
5553        case action_cleanup :
5554          do_cleanup (ap);
5555          break;
5556        case action_config :
5557          do_config (ap);
5558          break;
5559        case action_create :
5560          do_create (ap);
5561          break;
5562        case action_create_project :
5563          do_create_project (ap);
5564          break;
5565        case action_cvsbranches :
5566          do_cvsbranches (ap);
5567          break;
5568        case action_cvssubpackages :
5569          do_cvssubpackages (ap);
5570          break;
5571        case action_cvssubprojects :
5572          do_cvssubprojects (ap);
5573          break;
5574        case action_cvstags :
5575          do_cvstags (ap);
5576          break;
5577        case action_do :
5578          do_do (ap);
5579          break;
5580        case action_expand_model :
5581          do_expand_model (ap);
5582          break;
5583        case action_filter :
5584          do_filter (ap);
5585          break;
5586        case action_help :
5587          do_help (ap);
5588          break;
5589        case action_load :
5590          cerr << "#CMT> action not implemented" << endl;
5591          break;
5592        case action_lock :
5593          do_lock (ap);
5594          break;
5595        case action_relocate :
5596          do_relocate (ap);
5597          break;
5598        case action_remove :
5599          do_remove (ap);
5600          break;
5601        case action_remove_library_links :
5602          do_remove_library_links (ap);
5603          break;
5604        case action_run :
5605          do_run (ap);
5606          break;
5607        case action_run_sequence :
5608          do_run_sequence (ap);
5609          break;
5610        case action_set_version :
5611          do_set_version (ap);
5612          break;
5613        case action_set_versions :
5614          do_set_versions (ap);
5615          break;
5616        case action_setup :
5617          do_setup (ap);
5618          break;
5619        case action_show_action :
5620          do_show_action (ap);
5621          break;
5622        case action_show_action_names :
5623          do_show_action_names (ap);
5624          break;
5625        case action_show_action_value :
5626          do_show_action_value (ap);
5627          break;
5628        case action_show_actions :
5629          do_show_actions (ap);
5630          break;
5631        case action_show_all_tags :
5632          do_show_all_tags (ap);
5633          break;
5634        case action_show_applied_patterns :
5635          do_show_applied_patterns (ap);
5636          break;
5637        case action_show_author :
5638          do_show_author (ap);
5639          break;
5640        case action_show_branches :
5641          do_show_branches (ap);
5642          break;
5643        case action_show_clients :
5644          do_show_clients (ap);
5645          break;
5646        case action_show_cmtpath_patterns :
5647          do_show_cmtpath_patterns (ap);
5648          break;
5649        case action_show_constituent :
5650          do_show_constituent (ap);
5651          break;
5652        case action_show_constituent_names :
5653          do_show_constituent_names (ap);
5654          break;
5655        case action_show_constituents :
5656          do_show_constituents (ap);
5657          break;
5658        case action_show_cycles :
5659          do_show_cycles (ap);
5660          break;
5661        case action_show_fragment :
5662          do_show_fragment (ap);
5663          break;
5664        case action_show_fragments :
5665          do_show_fragments (ap);
5666          break;
5667        case action_show_groups :
5668          do_show_groups (ap);
5669          break;
5670        case action_show_include_dirs :
5671          do_show_include_dirs (ap);
5672          break;
5673        case action_show_language :
5674          do_show_language (ap);
5675          break;
5676        case action_show_languages :
5677          do_show_languages (ap);
5678          break;
5679        case action_show_macro :
5680          do_show_macro (ap);
5681          break;
5682        case action_show_macro_names :
5683          do_show_macro_names (ap);
5684          break;
5685        case action_show_macro_value :
5686          do_show_macro_value (ap);
5687          break;
5688        case action_show_macros :
5689          do_show_macros (ap);
5690          break;
5691        case action_show_manager :
5692          do_show_manager (ap);
5693          break;
5694        case action_show_packages :
5695          do_show_packages (ap);
5696          break;
5697        case action_show_path :
5698          do_show_path (ap);
5699          break;
5700        case action_show_pattern :
5701          do_show_pattern (ap);
5702          break;
5703        case action_show_pattern_names :
5704          do_show_pattern_names (ap);
5705          break;
5706        case action_show_patterns :
5707          do_show_patterns (ap);
5708          break;
5709        case action_show_projects :
5710          do_show_projects (ap);
5711          break;
5712        case action_show_project_author :
5713          do_show_project_author (ap);
5714          break;
5715        case action_show_pwd :
5716          do_show_pwd (ap);
5717          break;
5718        case action_show_setup :
5719          do_show_setup (ap);
5720          break;
5721        case action_show_set :
5722          do_show_set (ap);
5723          break;
5724        case action_show_set_names :
5725          do_show_set_names (ap);
5726          break;
5727        case action_show_set_value :
5728          do_show_set_value (ap);
5729          break;
5730        case action_show_sets :
5731          do_show_sets (ap);
5732          break;
5733        case action_show_strategies :
5734          do_show_strategies (ap);
5735          break;
5736        case action_show_tags :
5737          do_show_tags (ap);
5738          break;
5739        case action_show_use_paths :
5740          do_show_use_paths (ap);
5741          break;
5742        case action_show_uses :
5743          do_show_uses (ap);
5744          break;
5745        case action_show_version :
5746          do_show_version (ap);
5747          break;
5748        case action_show_versions :
5749          do_show_versions (ap);
5750          break;
5751        case action_system :
5752          do_show_system (ap);
5753          break;
5754        case action_unlock :
5755          do_unlock (ap);
5756          break;
5757        case action_version :
5758          do_version (ap);
5759          break;
5760        default:
5761          CmtError::set (CmtError::syntax_error, "ParseArguments>");
5762          break;
5763        }
5764    }
5765
5766  if (CmtError::has_pending_error ())
5767    {
5768      int code = CmtError::get_last_error_code ();     
5769      if (code == CmtError::execution_failed)
5770      {
5771          code = CmtError::get_last_execution_error();
5772      }   
5773     
5774      if (!Me.m_quiet) CmtError::print ();
5775      clear ();
5776      return (code);
5777    }
5778  else
5779    {
5780      clear ();
5781      return (0);
5782    }
5783}
5784
5785
5786/**
5787 * Format as one single line a set of 'setenv' statements
5788 * joined with semi-colons to form one shell command.
5789 */
5790void Cmt::print (PrintMode mode)
5791{
5792  Use::UsePtrVector& Uses = Use::get_ordered_uses ();
5793  Use& current_use = Use::current ();
5794
5795  cmt_string tag;
5796
5797  set_standard_macros ();
5798
5799    //cerr << "# current_tag=" << Me.m_current_tag << endl;
5800    //cerr << "# current_config=" << Me.m_current_config << endl;
5801
5802  if (Me.m_current_tag == "")
5803    {
5804      if (mode == Bat) tag = "%CMTCONFIG%";
5805      else tag = "${CMTCONFIG}";
5806    }
5807  else
5808    {
5809      tag = Me.m_current_tag;
5810    }
5811
5812    //
5813    //  Now check if all extra tags are still valid. Some of them
5814    //  may be discarded du to some conflict with highest priority
5815    //  tags, or with exclude statements
5816    //
5817
5818  {
5819    CmtSystem::cmt_string_vector words;
5820     
5821    cmt_string tags;
5822
5823    tags = Me.m_extra_tags;
5824     
5825    CmtSystem::split (tags, " \t,", words);
5826
5827    Me.m_extra_tags = ",";
5828     
5829    for (int i = 0; i < words.size (); i++)
5830      {
5831        Tag* tag;
5832        const cmt_string& a = words[i];
5833
5834        tag = Tag::find (a);
5835
5836        if ((tag != 0) && (tag->is_selected ()))
5837          {
5838            Me.m_extra_tags += a;
5839            Me.m_extra_tags += ",";
5840          }
5841      }
5842  }
5843
5844  if (Me.m_debug)
5845    {
5846      cout << "Before all print contexts" << endl;
5847    }
5848
5849  if (Uses.size () > 0)
5850    {
5851      int number;
5852
5853      for (number = 0; number < Uses.size (); number++)
5854        {
5855          Use& use = *(Uses[number]);
5856
5857          if (use.discarded) continue;
5858
5859          print_context (use, mode, tag);
5860        }
5861    }
5862
5863  print_context (Use::current (), mode, tag);
5864
5865  if (Me.m_debug)
5866    {
5867      cout << "After all print contexts" << endl;
5868    }
5869
5870  Symbol::all_print (mode);
5871  // Script::all_print (mode);
5872
5873  if (Me.m_debug)
5874    {
5875      cout << "After all print" << endl;
5876    }
5877
5878  cout << endl;
5879}
5880
5881
5882/**
5883 * Format as one single line a set of 'unsetenv' statements
5884 * joined with semi-colons to form one shell command.
5885 */
5886void Cmt::print_clean (PrintMode mode)
5887{
5888  Use::UsePtrVector& Uses = Use::get_ordered_uses ();
5889
5890  set_standard_macros ();
5891
5892  Script::all_print_clean (mode);
5893  Symbol::all_print_clean (mode);
5894
5895  switch (mode)
5896    {
5897    case Csh :
5898      if (Me.m_current_package != "CMT")
5899        {
5900          cout << "unsetenv " << Me.m_current_prefix << "ROOT" << endl;
5901          cout << "unsetenv " << Me.m_current_prefix << "CONFIG" << endl;
5902        }
5903      break;
5904    case Sh :
5905      if (Me.m_current_package != "CMT")
5906        {
5907          cout << "unset " << Me.m_current_prefix << "ROOT" << endl;
5908          cout << "unset " << Me.m_current_prefix << "CONFIG" << endl;
5909        }
5910      break;
5911    case Bat :
5912      if (Me.m_current_package != "CMT")
5913        {
5914          cout << "set " << Me.m_current_prefix << "ROOT=" << endl;
5915          cout << "set " << Me.m_current_prefix << "CONFIG=" << endl;
5916        }
5917      break;
5918    }
5919
5920  if (Uses.size () > 0)
5921    {
5922      int number;
5923
5924      for (number = 0; number < Uses.size (); number++)
5925        {
5926          Use* use = Uses[number];
5927
5928          if (use->discarded) continue;
5929          if (use->m_hidden) continue;
5930
5931          Package* p = use->get_package ();
5932          if (p->is_cmt ()) continue;
5933
5934          switch (mode)
5935            {
5936            case Csh :
5937              cout << "unsetenv " << use->prefix << "ROOT" << endl;
5938              cout << "unsetenv " << use->prefix << "CONFIG" << endl;
5939              break;
5940            case Sh :
5941              cout << "unset " << use->prefix << "ROOT" << endl;
5942              cout << "unset " << use->prefix << "CONFIG" << endl;
5943              break;
5944            case Bat :
5945              cout << "set " << use->prefix << "ROOT=" << endl;
5946              cout << "set " << use->prefix << "CONFIG" << endl;
5947              break;
5948            }
5949        }
5950    }
5951
5952  switch (mode)
5953    {
5954    case Csh :
5955      cout << "unsetenv CMTEXTRATAGS" << endl;
5956      break;
5957    case Sh :
5958      cout << "unset CMTEXTRATAGS" << endl;
5959      break;
5960    case Bat :
5961      cout << "set CMTEXTRATAGS=" << endl;
5962      break;
5963    }
5964
5965  cout << endl;
5966}
5967
5968//----------------------------------------------------------
5969void Cmt::print_context (Use& use, PrintMode mode, const cmt_string& tag)
5970{
5971  if (use.get_package_name () == "cmt_standalone") return;
5972
5973  cmt_string fs = CmtSystem::file_separator ();
5974
5975  use.real_path.replace_all (CmtSystem::file_separator (), fs);
5976
5977  cmt_string system = CmtSystem::get_cmt_config ();
5978
5979  bool do_config = use.get_strategy ("SetupConfig");
5980  bool do_root = use.get_strategy ("SetupRoot");
5981
5982  switch (mode)
5983    {
5984    case Csh :
5985      if (do_root)
5986        {
5987          cout << "setenv " << use.prefix << "ROOT \"" <<
5988            use.get_full_path () << "\"" << endl;
5989        }
5990
5991      if (use.get_package_name () == "CMT")
5992        {
5993          cout << "setenv CMTCONFIG " << system << endl;
5994        }
5995      else
5996        {
5997          if (do_config)
5998            {
5999              cout << "setenv " << use.prefix << "CONFIG \"" << tag << "\"" << endl;
6000            }
6001        }
6002       
6003      break;
6004    case Sh :
6005      if (do_root)
6006        {
6007          cout << use.prefix << "ROOT=\"" <<
6008            use.get_full_path () << "\"; export " <<
6009            use.prefix << "ROOT" << endl;
6010        }
6011
6012      if (use.get_package_name () == "CMT")
6013        {
6014          cout << "CMTCONFIG=" << system << "; export CMTCONFIG" << endl;
6015        }
6016      else
6017        {
6018          if (do_config)
6019            {
6020              cout << use.prefix << "CONFIG=\"" <<
6021                tag << "\"; export " <<
6022                use.prefix << "CONFIG" << endl;
6023            }
6024        }
6025       
6026      break;
6027    case Bat :
6028      if (do_root)
6029        {
6030          cout << "set " << use.prefix << "ROOT=" <<
6031            use.get_full_path () << endl;
6032        }
6033
6034      if (use.get_package_name () == "CMT")
6035        {
6036          cout << "set CMTCONFIG=" << system << endl;
6037        }
6038      else
6039        {
6040          if (do_config)
6041            {
6042              cout << "set " << use.prefix << "CONFIG=" << tag << endl;
6043            }
6044        }
6045       
6046      break;
6047    }
6048}
6049
6050/**
6051 *  Format a set of make macro definitions (one per line)
6052 * Each macro value is provided enclosed in single quotes
6053 *
6054 *  Take the macro values from the macro statements found
6055 * in recursively read requirements files.
6056 */
6057void Cmt::print_symbol_names (PrintMode mode, const cmt_string& pattern)
6058{
6059  int number;
6060
6061  set_standard_macros ();
6062
6063  cmt_regexp expression (pattern);
6064
6065  bool has_pattern = (pattern != "");
6066
6067  for (number = 0; number < Symbol::symbol_number (); number++)
6068    {
6069      Symbol& symbol = Symbol::symbol (number);
6070
6071      if (has_pattern)
6072       {
6073         if (!expression.match (symbol.name)) continue;
6074       }
6075
6076      if (Me.m_action == action_show_macro_names)
6077        {
6078          // Only keep macros.
6079          if ((symbol.type == Symbol::SymbolSet) ||
6080              (symbol.type == Symbol::SymbolAlias) ||
6081              (symbol.type == Symbol::SymbolPath) ||
6082              (symbol.type == Symbol::SymbolAction)) continue;
6083        }
6084      else if (Me.m_action == action_show_set_names)
6085        {
6086          // Exclude macros.
6087          if ((symbol.type == Symbol::SymbolMacro) ||
6088              (symbol.type == Symbol::SymbolAction)) continue;
6089        }
6090      else if (Me.m_action == action_show_action_names)
6091        {
6092          // Exclude macros.
6093          if (symbol.type != Symbol::SymbolAction) continue;
6094        }
6095
6096      cout << symbol.name << endl;
6097    }
6098}
6099
6100/**
6101 *  Format a set of make macro definitions (one per line)
6102 * Each macro value is provided enclosed in single quotes
6103 *
6104 *  Take the macro values from the macro statements found
6105 * in recursively read requirements files.
6106 */
6107void Cmt::print_macros (PrintMode mode, const cmt_string& pattern)
6108{
6109  int number;
6110
6111  set_standard_macros ();
6112
6113  cmt_regexp expression (pattern);
6114
6115  bool has_pattern = (pattern != "");
6116
6117  for (number = 0; number < Symbol::symbol_number (); number++)
6118    {
6119      Symbol& symbol = Symbol::symbol (number);
6120
6121      if (has_pattern)
6122        {
6123          if (!expression.match (symbol.name)) continue;
6124        }
6125
6126      if (Me.m_action == action_show_macros)
6127        {
6128          // Only keep macros.
6129          if ((symbol.type == Symbol::SymbolSet) ||
6130              (symbol.type == Symbol::SymbolAlias) ||
6131              (symbol.type == Symbol::SymbolPath) ||
6132              (symbol.type == Symbol::SymbolAction)) continue;
6133        }
6134      else if (Me.m_action == action_show_sets)
6135        {
6136          // Exclude macros.
6137          if ((symbol.type == Symbol::SymbolMacro) ||
6138              (symbol.type == Symbol::SymbolAction)) continue;
6139        }
6140      else if (Me.m_action == action_build_tag_makefile)
6141        {
6142          // Exclude scripts and actions
6143          if ((symbol.type == Symbol::SymbolSetupScript) ||
6144              (symbol.type == Symbol::SymbolCleanupScript) ||
6145              (symbol.type == Symbol::SymbolAction)) continue;
6146        }
6147      else if (Me.m_action == action_show_actions)
6148        {
6149          if (symbol.type != Symbol::SymbolAction) continue;
6150        }
6151
6152      if (symbol.value_lists.size () < 1) continue;
6153
6154      symbol.show_macro (mode);
6155    }
6156}
6157
6158//----------------------------------------------------------
6159void Cmt::print_tabs (int tabs)
6160{
6161  while (tabs > 0)
6162    {
6163      cout << "  ";
6164      tabs--;
6165    }
6166}
6167
6168//----------------------------------------------------------
6169int Cmt::reach_current_package ()
6170{
6171  Use& use = Use::current ();
6172  cmt_string dir;
6173
6174  if (Me.m_debug)
6175    {
6176      cout << "Cmt::reach_current_package> pwd = " 
6177           << CmtSystem::pwd () 
6178           << " path=" << Me.m_current_path
6179           << " package=" << Me.m_current_package
6180           << endl;
6181    }
6182
6183  /*
6184    Try to access the package.
6185  */
6186
6187  if (Me.m_current_package == "cmt_standalone")
6188    {
6189      if ((Me.m_current_path != "") && (Me.m_current_path != CmtSystem::pwd ()))
6190        {
6191          if (!CmtSystem::cd (Me.m_current_path))
6192            {
6193              CmtError::set (CmtError::package_not_found,
6194                             "ReachCurrentPackage> Cannot reach the path directory");
6195              return (0);
6196            }
6197        }
6198
6199      if (!CmtSystem::test_file ("requirements"))
6200        {
6201            /*
6202          if (!Me.m_quiet)
6203            {
6204              cout << "#CMT> Cannot reach the requirements file" << endl;
6205            }
6206             
6207          CmtError::set (CmtError::package_not_found,
6208                         "ReachCurrentPackage> Cannot reach the requirements file");
6209            */
6210          return (0);
6211        }
6212    }
6213  else if (Me.m_current_package != "")
6214    {
6215      if (!use.move_to ())
6216        {
6217          CmtError::set (CmtError::package_not_found,
6218                         "ReachCurrentPackage> Cannot reach the path directory");
6219          return (0);
6220        }
6221
6222      Me.m_current_path = use.real_path;
6223    }
6224  else
6225    {
6226      //
6227      // The cmt command has been given without explicit search for
6228      // a package. Thus it is expected that we are in the context of a
6229      // true package.
6230      //
6231      //  This means that there should be a requirements file visible.
6232      //
6233      //  If this is not true, we'll make a try into ../cmt and then
6234      // a last try into ../mgr
6235      //
6236
6237      if (!CmtSystem::test_file ("requirements"))
6238        {
6239          if (CmtSystem::cd ("../cmt") && 
6240              CmtSystem::test_file ("requirements"))
6241            {
6242              Me.m_current_style = cmt_style;
6243            }
6244          else if (CmtSystem::cd ("../mgr") && 
6245                   CmtSystem::test_file ("requirements"))
6246            {
6247              Me.m_current_style = mgr_style;
6248            }
6249          else
6250            {
6251              if (!Me.m_quiet)
6252                {
6253                  cerr << "#CMT> Cannot reach the mgr branch" << endl;
6254                }
6255             
6256              CmtError::set (CmtError::package_not_found,
6257                             "ReachCurrentPackage> Cannot reach the mgr/cmt directory");
6258              return (0);
6259            }
6260        }
6261
6262      dir = CmtSystem::pwd ();
6263
6264      CmtSystem::dirname (dir, Me.m_current_path);
6265      CmtSystem::basename (Me.m_current_path, Me.m_current_version);
6266
6267      if (CmtSystem::is_version_directory (Me.m_current_version))
6268        {
6269          CmtSystem::dirname (Me.m_current_path, Me.m_current_path);
6270          CmtSystem::basename (Me.m_current_path, Me.m_current_package);
6271          CmtSystem::dirname (Me.m_current_path, Me.m_current_path);
6272        }
6273      else
6274        {
6275          Me.m_current_package = Me.m_current_version;
6276          Me.m_current_version = "";
6277          CmtSystem::dirname (Me.m_current_path, Me.m_current_path);
6278
6279          Me.m_current_style = no_version_style;
6280        }
6281
6282      use.set_package_name (Me.m_current_package);
6283      use.version = Me.m_current_version;
6284      use.path    = Me.m_current_path;
6285      use.style   = Me.m_current_style;
6286    }
6287
6288  configure_current_dir ();
6289  build_prefix (Me.m_current_package, Me.m_current_prefix);
6290  build_config (Me.m_current_prefix, Me.m_current_config);
6291
6292  /*
6293    Check Tag is always set up
6294  */
6295
6296  if (Me.m_debug) cout << "reach_current_package0> current_tag=" << Me.m_current_tag << endl;
6297
6298  if (Me.m_current_tag == "")
6299    {
6300      cmt_string env;
6301
6302      env = CmtSystem::getenv (Me.m_current_config);
6303      if (env != "")
6304        {
6305          Tag* tag;
6306
6307          tag = Tag::add (env, PriorityConfig, "reach current package", 0);
6308          tag->mark ();
6309            //Me.m_current_tag = env;
6310
6311          //if (!Me.m_quiet) cerr << "reach_current_package1> current_tag=" << Me.m_current_tag << endl;
6312
6313        }
6314    }
6315
6316  if (Me.m_debug)
6317    {
6318      cout << "pwd = " << CmtSystem::pwd () << endl;
6319    }
6320
6321  /*
6322    Work on the requirements file.
6323  */
6324
6325  if (dir != "") dir += CmtSystem::file_separator ();
6326  dir += "requirements";
6327  SyntaxParser::parse_requirements (dir, &use);
6328
6329  if (Me.m_debug) cout << "reach_current_package2> current_tag=" << Me.m_current_tag << endl;
6330
6331    /**
6332     *   It would be useful to change this mechanism. Instead of
6333     *  applying all global patterns at once to all use contexts, it
6334     *  would be much better to apply it at the end of each
6335     *  requirements file parsing, and only in the context the
6336     *  appropriate Use.
6337     *
6338     *   This would avoid the current flaw which is that when a global
6339     *  pattern specifies a "private" definition, it is actually
6340     *  applied in the scope context of the Current Use and not in
6341     *  each individual Use. Therefore the private is lost.
6342     *
6343     *   However, this induces problems since some pattern definitions
6344     *  are done AFTER the use statements, which will NOT receive the
6345     *  pattern aplications.
6346     *
6347     *   Therefore it is decided to leave this "bad" mechanism until
6348     *  everybody is aware of this constraint.
6349     *
6350     *
6351     */
6352  Pattern::apply_all_globals ();
6353
6354  /*
6355    Select all possible tags
6356  */
6357
6358  Tag::restore_tree ();
6359
6360  return (1);
6361}
6362
6363static cmt_string get_best_form (const CmtSystem::cmt_string_vector& pwd,
6364                                 const cmt_string& path)
6365{
6366  static cmt_string fs = CmtSystem::file_separator ();
6367  cmt_string result;
6368
6369    /*
6370    //if (CmtSystem::getenv ("CMTTESTPREFIX") != "")
6371    {
6372    */
6373
6374    //
6375    //  If there is a common prefix between
6376    //  use->real_path and pwd
6377    //  we have
6378    //  use->real_path = /<prefix>/aaa
6379    //  pwd            = /<prefix>/bbb
6380    //
6381    //  Then use->real_path may be expressed as:
6382    //  ../..../../aaa
6383    //   where ../..../../ moves up to /<prefix>
6384    //
6385    //   Then we try to find the shortest between
6386    //
6387    //     /<prefix> and ../..../..
6388    //
6389  cmt_string a = path;
6390 
6391  CmtSystem::cmt_string_vector va;
6392 
6393  va.clear ();
6394 
6395  CmtSystem::split (a, fs, va);
6396 
6397  int m = va.size ();
6398  if (pwd.size () < m) m = pwd.size ();
6399 
6400  int i;
6401 
6402    //cout << "Package " << use->get_package_name () << endl;
6403 
6404  for (i = 0; i < m; i++)
6405    {
6406      const cmt_string& fa = va[i];
6407      const cmt_string& fb = pwd[i];
6408     
6409        //cout << "  fa=" << fa << " fb=" << fb << endl;
6410     
6411      if (fa != fb) break;
6412    }
6413 
6414  cmt_string ups = "";
6415 
6416  if (i > 0)
6417    {
6418        // We have the prefix.
6419        // if we count what remains from pwd, then
6420        // we have the number of ../ required to
6421        // move to /<prefix>
6422      int j;
6423     
6424      for (j = i; j < pwd.size (); j++)
6425        {
6426          if (j > i) ups += fs;
6427          ups += "..";
6428        }
6429
6430      for (j = i; j < va.size (); j++)
6431        {
6432          ups += fs;
6433          ups += va[j];
6434        }
6435    }
6436 
6437    //
6438    // Here ups contains the ../..../../aaa form
6439    // for the use->real_path or is empty when there
6440    // were no common prefix.
6441    //
6442 
6443    //if (ups != "")
6444  if ((ups != "") &&
6445      (ups.size () < path.size ()))
6446    {
6447      result = ups;
6448    }
6449  else
6450    {
6451      result = path;
6452    }
6453
6454  return (result);
6455}
6456
6457/**
6458 *   This completely local class holds primitive actions for building
6459 *   standard macros.
6460 */
6461class StandardMacroBuilder
6462{
6463public:
6464
6465  /**
6466   *  CMTVERSION
6467   */
6468  void fill_for_CMTVERSION ()
6469  {
6470    buffer = "macro CMTVERSION \"";
6471    buffer += CMTVERSION;
6472    buffer += "\"";
6473    apply ();
6474  }
6475
6476  StandardMacroBuilder (const cmt_string& tag,
6477                        const cmt_string& package,
6478                        const cmt_string& version,
6479                        const cmt_string& prefix,
6480                        CmtDirStyle style)
6481  {
6482    fs = CmtSystem::file_separator ();
6483    buffer = "";
6484    pwd = CmtSystem::pwd ();
6485    CmtSystem::split (pwd, fs, vb);
6486    current_use = &(Use::current ());
6487    current_tag = tag;
6488    current_package = package;
6489    current_version = version;
6490    current_prefix = prefix;
6491    current_style = style;
6492  }
6493
6494  void apply ()
6495  {
6496    SyntaxParser::parse_requirements_line (buffer, current_use);
6497    buffer = "";
6498  }
6499
6500  /**
6501   *   tag
6502   */
6503  void fill_for_tag ()
6504  {
6505    static bool tag_debug = CmtSystem::testenv ("TAGDEBUG");
6506
6507    if (!Symbol::is_selected ("tag"))
6508      {
6509        if (tag_debug) cerr << "set_standard_macro2.1> current_tag=" << current_tag << endl;
6510
6511        if (current_tag == "")
6512          {
6513            buffer = "macro tag \"$(CMTCONFIG)\"";
6514          }
6515        else
6516          {
6517            buffer = "macro tag \"";
6518            buffer += current_tag;
6519            buffer += "\"";
6520          }
6521       
6522        if (tag_debug) cerr << " define tag: " << buffer << endl;
6523       
6524        apply ();
6525      }
6526  }
6527
6528  /**
6529   *   PACKAGE_ROOT
6530   */
6531  void fill_for_package (const cmt_string& current_dir)
6532  {
6533    buffer = "macro package \"";
6534    buffer += current_package;
6535    buffer += "\"";
6536    apply ();
6537
6538    buffer = "macro version \"";
6539    buffer += current_version;
6540    buffer += "\"";
6541    apply ();
6542
6543    if (!Symbol::is_selected ("PACKAGE_ROOT"))
6544      {
6545        buffer = "macro PACKAGE_ROOT \"$(";
6546        buffer += current_prefix;
6547        buffer += "ROOT";
6548        buffer += ")\"";
6549
6550        apply ();
6551      }
6552  }
6553
6554  /**
6555   *   srcdir
6556   *   src       =$(srcdir)/
6557   *   inc
6558   *   mgrdir
6559   *   mgr       =../$(mgrdir)/
6560   *   bin
6561   *   javabin
6562   *   doc
6563   *   version
6564   *   package
6565   *
6566   *   <package>_project
6567   *   <package>_cmtpath
6568   *   <package>_offset
6569   *   package_cmtpath
6570   *   package_offset
6571   *   project
6572   *
6573   */
6574  void fill_for_branches ()
6575  {
6576    /**
6577     *    Basic macros  (src, mgr, ...)
6578     */
6579   
6580    if (current_style == none_style)
6581      {
6582        buffer = "macro srcdir \".";
6583        buffer += "\"";
6584        apply ();
6585
6586        buffer = "macro src \".";
6587        buffer += fs;
6588        buffer += "\"";
6589        apply ();
6590
6591        buffer = "macro inc \".";
6592        buffer += fs;
6593        buffer += "\"";
6594        apply ();
6595
6596        buffer = "macro mgr \".";
6597        buffer += fs;
6598        buffer += "\"";
6599        apply ();
6600
6601        buffer = "macro bin \".";
6602        buffer += fs;
6603        buffer += "\"";
6604        apply ();
6605
6606        buffer = "macro javabin \".";
6607        buffer += fs;
6608        buffer += "\"";
6609        apply ();
6610
6611        buffer = "macro doc \".";
6612        buffer += fs;
6613        buffer += "\"";
6614        apply ();
6615      }
6616    else
6617      {
6618        if (!Symbol::is_selected ("srcdir"))
6619          {
6620            buffer = "macro srcdir \"..";
6621            buffer += fs;
6622            buffer += "src";
6623            buffer += "\"";
6624            apply ();
6625          }
6626       
6627        if (!Symbol::is_selected ("src"))
6628          {
6629            buffer = "macro src \"..";
6630            buffer += fs;
6631            buffer += "src";
6632            buffer += fs;
6633            buffer += "\"";
6634            apply ();
6635          }
6636       
6637        if (!Symbol::is_selected ("inc"))
6638          {
6639            buffer = "macro inc \"..";
6640            buffer += fs;
6641            buffer += "src";
6642            buffer += fs;
6643            buffer += "\"";
6644            apply ();
6645          }
6646       
6647        if (!Symbol::is_selected ("doc"))
6648          {
6649            buffer = "macro doc \"..";
6650            buffer += fs;
6651            buffer += "doc";
6652            buffer += fs;
6653            buffer += "\"";
6654            apply ();
6655          }
6656       
6657        if (!Symbol::is_selected ("bin"))
6658          {
6659            cmt_string package_tag = current_package;
6660            package_tag += "_tag";
6661
6662            buffer = "macro bin \"..";
6663            buffer += fs;
6664            buffer += "$(";
6665            buffer += package_tag;
6666            buffer += ")";
6667            buffer += fs;
6668            buffer += "\"";
6669            apply ();
6670          }
6671
6672        if (!Symbol::is_selected ("javabin"))
6673          {
6674            buffer = "macro javabin \"..";
6675            buffer += fs;
6676            buffer += "classes";
6677            buffer += fs;
6678            buffer += "\"";
6679            apply ();
6680          }
6681       
6682        if (current_style == mgr_style)
6683          {
6684            buffer = "macro mgrdir \"mgr\"";
6685            apply ();
6686
6687            buffer = "macro mgr \"..";
6688            buffer += fs;
6689            buffer += "mgr";
6690            buffer += fs;
6691            buffer += "\"";
6692            apply ();
6693          }
6694        else
6695          {
6696            buffer = "macro mgrdir \"cmt\"";
6697            apply ();
6698
6699            buffer = "macro mgr \"..";
6700            buffer += fs;
6701            buffer += "cmt";
6702            buffer += fs;
6703            buffer += "\"";
6704            apply ();
6705          }
6706
6707        Cmt::configure_current_cmtpath ();
6708      }
6709  }
6710
6711  /**
6712   *   project
6713   */
6714  void fill_for_project ()
6715  {
6716    if (current_style == none_style) return;
6717
6718    cmt_string project_name;
6719    Project* project = Project::get_current ();
6720    if (project != 0)
6721      {
6722        project_name = project->get_name ();
6723      }
6724
6725    buffer = "macro project \"";
6726    buffer += project_name;
6727    buffer += "\"";
6728    apply ();
6729  }
6730
6731  /**
6732   *   use_requirements
6733   */
6734  void fill_for_use_requirements ()
6735  {
6736    Use::UsePtrVector& Uses = Use::get_ordered_uses ();
6737
6738    if (Uses.size () == 0) return;
6739
6740    if (!Symbol::is_selected ("use_requirements"))
6741      {
6742        buffer  = "macro use_requirements \"";
6743        buffer += "requirements ";
6744       
6745        for (int number = 0; number < Uses.size (); number++)
6746          {
6747            Use* use = Uses[number];
6748           
6749            if (use->discarded) continue;
6750            if (use->m_hidden) continue;
6751           
6752            if (use->located ())
6753              {
6754                buffer += "$(";
6755                buffer += use->prefix;
6756                buffer += "ROOT)";
6757                buffer += fs;
6758               
6759                if (use->style == mgr_style) buffer += "mgr";
6760                else buffer += "cmt";
6761               
6762                buffer += fs;
6763                buffer += "requirements ";
6764              }
6765          }
6766       
6767        buffer += "\"";
6768       
6769        apply ();
6770      }
6771  }
6772
6773  /**
6774   *   use_includes
6775   */
6776  void fill_for_use_includes ()
6777  {
6778    Include::parse_all (&(Use::current()));
6779
6780    Use::UsePtrVector& Uses = Use::get_ordered_uses ();
6781
6782    if (Uses.size () == 0) return;
6783
6784    if (!Symbol::is_selected ("use_includes"))
6785      {
6786        buffer = "macro_append use_includes \' ";
6787       
6788        for (int number = 0; number < Uses.size (); number++)
6789          {
6790            Use* use = Uses[number];
6791           
6792            if (use->discarded) continue;
6793            if (use->m_hidden) continue;
6794
6795            Package* p = use->get_package ();
6796            if (p->is_cmt ()) continue;
6797
6798            if (Cmt::get_debug ())
6799              {
6800                cout << "fill use_includes for " << use->get_package_name () 
6801                     << " discarded=" << use->discarded
6802                     << " auto_imports=" << use->auto_imports << endl;
6803              }
6804           
6805            if (use->auto_imports == Off) continue;
6806           
6807            Include::parse_all (use);
6808
6809            use->fill_includes_macro (buffer);
6810          }
6811       
6812        buffer += "\'";
6813       
6814        apply ();
6815      }
6816  }
6817
6818  /**
6819   *   use_fincludes
6820   */
6821  void fill_for_use_fincludes ()
6822  {
6823    Use::UsePtrVector& Uses = Use::get_ordered_uses ();
6824
6825    if (Uses.size () == 0) return;
6826
6827    if (!Symbol::is_selected ("use_fincludes"))
6828      {
6829        buffer = "macro_append use_fincludes \" $(use_includes)\"";
6830        apply ();
6831      }
6832  }
6833
6834  /**
6835   *   use_stamps
6836   */
6837  void fill_for_use_stamps ()
6838  {
6839    Use::UsePtrVector& Uses = Use::get_ordered_uses ();
6840
6841    if (Uses.size () == 0) return;
6842
6843    if (!Symbol::is_selected ("use_stamps"))
6844      {
6845        buffer = "macro use_stamps \"";
6846        (Use::current()).fill_macro (buffer, "stamps");
6847       
6848        for (int number = 0; number < Uses.size (); number++)
6849          {
6850            Use* use = Uses[number];
6851           
6852            if (use->discarded) continue;
6853            if (use->m_hidden) continue;
6854
6855            Package* p = use->get_package ();
6856            if (p->is_cmt ()) continue;
6857           
6858            use->fill_macro (buffer, "stamps");
6859          }
6860       
6861        buffer += "\"";
6862       
6863        apply ();
6864      }
6865  }
6866
6867  /**
6868   *   use_cflags
6869   */
6870  void fill_for_use_cflags ()
6871  {
6872    Use::UsePtrVector& Uses = Use::get_ordered_uses ();
6873
6874    if (Uses.size () == 0) return;
6875
6876    if (!Symbol::is_selected ("use_cflags"))
6877      {
6878        Use::fill_macro_all (buffer, "cflags");
6879        apply ();
6880      }
6881  }
6882
6883  /**
6884   *   use_pp_cflags
6885   */
6886  void fill_for_use_pp_cflags ()
6887  {
6888    Use::UsePtrVector& Uses = Use::get_ordered_uses ();
6889
6890    if (Uses.size () == 0) return;
6891
6892    if (!Symbol::is_selected ("use_pp_cflags"))
6893      {
6894        Use::fill_macro_all (buffer, "pp_cflags");
6895        apply ();
6896      }
6897  }
6898
6899  /**
6900   *   use_cppflags
6901   */
6902  void fill_for_use_cppflags ()
6903  {
6904    Use::UsePtrVector& Uses = Use::get_ordered_uses ();
6905
6906    if (Uses.size () == 0) return;
6907
6908    if (!Symbol::is_selected ("use_cppflags"))
6909      {
6910        Use::fill_macro_all (buffer, "cppflags");
6911        apply ();
6912      }
6913  }
6914
6915  /**
6916   *   use_pp_cppflags
6917   */
6918  void fill_for_use_pp_cppflags ()
6919  {
6920    Use::UsePtrVector& Uses = Use::get_ordered_uses ();
6921
6922    if (Uses.size () == 0) return;
6923
6924    if (!Symbol::is_selected ("use_pp_cppflags"))
6925      {
6926        Use::fill_macro_all (buffer, "pp_cppflags");
6927        apply ();
6928      }
6929  }
6930
6931  /**
6932   *   use_fflags
6933   */
6934  void fill_for_use_fflags ()
6935  {
6936    Use::UsePtrVector& Uses = Use::get_ordered_uses ();
6937
6938    if (Uses.size () == 0) return;
6939
6940    if (!Symbol::is_selected ("use_fflags"))
6941      {
6942        Use::fill_macro_all (buffer, "fflags");
6943        apply ();
6944      }
6945  }
6946
6947  /**
6948   *   use_pp_fflags
6949   */
6950  void fill_for_use_pp_fflags ()
6951  {
6952    Use::UsePtrVector& Uses = Use::get_ordered_uses ();
6953
6954    if (Uses.size () == 0) return;
6955
6956    if (!Symbol::is_selected ("use_pp_fflags"))
6957      {
6958        Use::fill_macro_all (buffer, "pp_fflags");
6959        apply ();
6960      }
6961  }
6962
6963  /**
6964   *   use_linkopts
6965   */
6966  void fill_for_use_linkopts ()
6967  {
6968    Use::UsePtrVector& Uses = Use::get_ordered_uses ();
6969
6970    if (Uses.size () == 0) return;
6971
6972    if (!Symbol::is_selected ("use_linkopts"))
6973      {
6974        Use::fill_macro_all (buffer, "linkopts");
6975        apply ();
6976      }
6977  }
6978
6979  /**
6980   *   use_libraries
6981   */
6982  void fill_for_use_libraries ()
6983  {
6984    Use::UsePtrVector& Uses = Use::get_ordered_uses ();
6985
6986    if (Uses.size () == 0) return;
6987
6988    if (!Symbol::is_selected ("use_libraries"))
6989      {
6990        buffer  = "macro use_libraries \"";
6991
6992        for (int number = 0; number < Uses.size (); number++)
6993          {
6994            Use* use = Uses[number];
6995           
6996            if (use->discarded) continue;
6997            if (use->m_hidden) continue;
6998           
6999            Package* p = use->get_package ();
7000            if (p->is_cmt ()) continue;
7001
7002            use->fill_macro (buffer, "libraries");
7003          }
7004       
7005        buffer += "\"";
7006       
7007        apply ();
7008      }
7009  }
7010
7011  /**
7012   *   includes
7013   */
7014  void fill_for_includes ()
7015  {
7016    Use::UsePtrVector& Uses = Use::get_ordered_uses ();
7017
7018    if (Uses.size () == 0) return;
7019
7020    if (!Symbol::is_selected ("includes"))
7021      {
7022        buffer = "macro_append includes \' ";
7023
7024        Use& use = Use::current();
7025
7026        if (use.include_path == "")
7027          {
7028            buffer += "$(ppcmd)\"$(srcdir)\" ";
7029          }
7030        else if (use.include_path != "none")
7031          {
7032            buffer += "$(ppcmd)\"";
7033            buffer += use.include_path;
7034            buffer += "\" ";
7035          }
7036
7037        for (int include_number = 0;
7038             include_number < use.includes.size ();
7039             include_number++)
7040          {
7041            Include& incl = use.includes[include_number];
7042
7043            if (incl.name == "") continue;
7044
7045            buffer += "$(ppcmd)\"";
7046            buffer += incl.name;
7047            buffer += "\" ";
7048          }
7049       
7050        buffer += "$(use_includes)\'";
7051       
7052        apply ();
7053      }
7054  }
7055
7056  /**
7057   *   fincludes
7058   */
7059  void fill_for_fincludes ()
7060  {
7061    Use::UsePtrVector& Uses = Use::get_ordered_uses ();
7062
7063    if (Uses.size () == 0) return;
7064
7065    if (!Symbol::is_selected ("fincludes"))
7066      {
7067        buffer = "macro_append fincludes \" $(includes)\"";
7068        apply ();
7069      }
7070  }
7071
7072  /**
7073   *  Macros specific to constituents.
7074   *  This includes the compiler flags
7075   *  and fills in these macros from uses packages. This takes care
7076   *  of -no_auto_imports and -import= directives
7077   *
7078   *    <constituent>_use_linkopts
7079   *    <prefix>_<constituent>_cflags
7080   *    <prefix>_<constituent>_pp_cflags
7081   *    <prefix>_<constituent>_cppflags
7082   *    <prefix>_<constituent>_pp_cppflags
7083   *    <prefix>_<constituent>_fflags
7084   *    <prefix>_<constituent>_pp_fflags
7085   *    <constituent>linkopts
7086   *    <constituent>_GUID
7087   *
7088   */
7089  void fill_for_all_constituents ()
7090  {
7091    /// First, finish the parsing of constituent parameters.
7092    if (Cmt::get_debug ())
7093      {
7094        cout << "fill_for_all_constituents>" << endl;
7095      }
7096    Constituent::parse_all ();
7097
7098    Use::UsePtrVector& Uses = Use::get_ordered_uses ();
7099
7100    const Constituent::ConstituentVector& constituents =
7101    Constituent::constituents ();
7102
7103 
7104    /// Prepare the auto_imports states in a vector
7105    cmt_vector<bool> base_auto_imports_states;
7106
7107    base_auto_imports_states.resize (Uses.size ());
7108
7109    int number;
7110
7111    for (number = 0; number < Uses.size (); number++)
7112      {
7113        Use* use = Uses[number];
7114        base_auto_imports_states[number] = (use->auto_imports != Off);
7115      }
7116
7117    /// Now scan all constituents
7118
7119    for (number = 0; number < constituents.size (); number++)
7120      {
7121        const Constituent& constituent = constituents[number];
7122
7123        if (Cmt::get_debug ())
7124          {
7125            cout << "Checking " << constituent.name  << " against imports requests" << endl;
7126          }
7127        Use::UsePtrVector imports;
7128        int i;
7129
7130        /**
7131         *  Problem for imports in constituents.
7132         *
7133         *     1) use_xxx has holes due to the corresponding
7134         *         -no_auto_imports options attached to some
7135         *        use statements (including the transitive ones)
7136         *
7137         *     2) the -import=yyy options provided to a given constituent
7138         *        should restore the appropriate holes as well as
7139         *        all transitive ones.
7140         *
7141         *     3) for use_linkopts, missing pieces must be filled at
7142         *        the right position. (for others, order is not relevant
7143         *        while transitive access is required for all)
7144         *
7145         */
7146
7147        if (constituent.type == Document)
7148          { 
7149            continue;
7150          }
7151
7152        if (constituent.imports.size () == 0) 
7153          {
7154            buffer = "macro_append ";
7155            buffer += constituent.name;
7156            buffer += "_use_linkopts ";
7157            buffer += " \" ";
7158       
7159            current_use->fill_macro (buffer, "linkopts");
7160       
7161            for (i = 0; i < Uses.size (); i++)
7162              {
7163                if (base_auto_imports_states[i])
7164                  {
7165                    Use* u = Uses[i];
7166               
7167                    if (u->discarded) continue;
7168
7169                            Package* p = u->get_package ();
7170                            if (p->is_cmt ()) continue;
7171                   
7172                    u->fill_macro (buffer, "linkopts");
7173                  }
7174              }
7175            buffer += "\"";
7176            apply ();
7177
7178          /*
7179            buffer = "macro_append ";
7180            buffer += constituent.name;
7181            buffer += "_use_linkopts ";
7182
7183            buffer += " \" $(use_linkopts)\"";
7184            apply ();
7185            */
7186
7187            continue;
7188          }
7189
7190        // From here on, the constituent HAS import options.
7191
7192        /**
7193         * Create a private copy of the state vector. This private copy
7194         * will be updated according to -import=xxx modifiers for the
7195         * current constituent.
7196         */
7197        cmt_vector<bool> auto_imports_states (base_auto_imports_states);
7198
7199        for (i = 0; i < constituent.imports.size (); i++)
7200          {
7201            const cmt_string& import = constituent.imports[i];
7202           
7203            //
7204            // Resolve the imported uses
7205            //
7206
7207            int use_index = Use::find_index (import, "", "");
7208
7209            if (use_index >= 0)
7210              {
7211                Use* u = Uses[use_index];
7212           
7213                if (u->discarded) continue;
7214               
7215                if (Cmt::get_debug ())
7216                  {
7217                    cout << constituent.name  << " needs imports " << import << " "
7218                         << use_index << " " 
7219                         << u->get_package()->get_name() << " "
7220                         << " u->auto_imports=" << u->auto_imports
7221                         << " Off=" << Off
7222                         << " On=" << On
7223                         << endl;
7224                  }
7225
7226                Package* p = u->get_package ();
7227                if (p->is_cmt ()) continue;
7228
7229                if (u->auto_imports != Off) continue;
7230
7231                Use::set_auto_imports_state (use_index, auto_imports_states);
7232              }
7233          }
7234
7235        if (Cmt::get_debug ())
7236          {
7237            cout << constituent.name  << " has imports " << endl;
7238          }
7239
7240
7241        /**
7242         *   Find all newly exposed packages and precompute this list inside
7243         *   a vector.
7244         */
7245        for (i = 0; i < base_auto_imports_states.size (); i++)
7246          {
7247            if (base_auto_imports_states[i]== On && auto_imports_states[i] == Off) continue;
7248           
7249            Use* u = Uses[i];
7250
7251            if (u->discarded) continue;
7252            if (u->m_hidden)  continue;
7253           
7254            Package* p = u->get_package ();
7255            if (p->is_cmt ()) continue;
7256           
7257            if (Cmt::get_debug ())
7258              {
7259                cout << constituent.name  << " has import " << p->get_name () << endl;
7260              }
7261           
7262            imports.push_back (u);
7263          }
7264       
7265        if (imports.size () == 0) continue;
7266
7267        cmt_string prefix;
7268           
7269        //
7270        // Documents are not considered
7271        //
7272        switch (constituent.type)
7273          {
7274          case Application:
7275            prefix = "app_";
7276            break;
7277          case Library:
7278            prefix = "lib_";
7279            break;
7280          }
7281           
7282        buffer = "macro_append ";
7283        buffer += prefix;
7284        buffer += constituent.name;
7285        buffer += "_cflags ";
7286        buffer += " \' ";
7287        for (i = 0; i < imports.size (); i++)
7288          {
7289            Use* u = imports[i];
7290           
7291            u->fill_includes_macro (buffer);
7292            u->fill_macro (buffer, "cflags");
7293          }
7294        buffer += "\'";
7295        apply ();
7296       
7297        buffer = "macro_append ";
7298        buffer += prefix;
7299        buffer += constituent.name;
7300        buffer += "_pp_cflags ";
7301        buffer += " \" ";
7302        for (i = 0; i < imports.size (); i++)
7303          {
7304            Use* u = imports[i];
7305           
7306            u->fill_macro (buffer, "pp_cflags");
7307          }
7308        buffer += "\"";
7309        apply ();
7310       
7311        buffer = "macro_append ";
7312        buffer += prefix;
7313        buffer += constituent.name;
7314        buffer += "_cppflags ";
7315        buffer += " \' ";
7316        for (i = 0; i < imports.size (); i++)
7317          {
7318            Use* u = imports[i];
7319           
7320            u->fill_includes_macro (buffer);
7321            u->fill_macro (buffer, "cppflags");
7322          }
7323        buffer += "\'";
7324        apply ();
7325       
7326        buffer = "macro_append ";
7327        buffer += prefix;
7328        buffer += constituent.name;
7329        buffer += "_pp_cppflags ";
7330        buffer += " \" ";
7331        for (i = 0; i < imports.size (); i++)
7332          {
7333            Use* u = imports[i];
7334           
7335            u->fill_macro (buffer, "pp_cppflags");
7336          }
7337        buffer += "\"";
7338        apply ();
7339       
7340        buffer = "macro_append ";
7341        buffer += prefix;
7342        buffer += constituent.name;
7343        buffer += "_fflags ";
7344        buffer += " \' ";
7345        for (i = 0; i < imports.size (); i++)
7346          {
7347            Use* u = imports[i];
7348           
7349            u->fill_includes_macro (buffer);
7350            u->fill_macro (buffer, "fflags");
7351          }
7352        buffer += "\'";
7353        apply ();
7354       
7355        buffer = "macro_append ";
7356        buffer += prefix;
7357        buffer += constituent.name;
7358        buffer += "_pp_fflags ";
7359        buffer += " \" ";
7360        for (i = 0; i < imports.size (); i++)
7361          {
7362            Use* u = imports[i];
7363           
7364            u->fill_macro (buffer, "pp_fflags");
7365          }
7366        buffer += "\"";
7367        apply ();
7368       
7369        /**
7370           *  Setting ${CONSTITUENT}linkopts is a temporary solution
7371           *  until the backward compatibility solution for a proper
7372           *  replacement of use_linkopts by ${CONSTITUENT}_use_linkopts
7373           *  is acheived.
7374           *
7375           */
7376       buffer = "macro_append ";
7377       buffer += constituent.name;
7378       buffer += "linkopts ";
7379       buffer += " \" ";
7380       for (i = 0; i < imports.size (); i++)
7381         {
7382           Use* u = imports[i];
7383           
7384           u->fill_macro (buffer, "linkopts");
7385         }
7386       buffer += "\"";
7387       apply ();
7388       
7389       /**
7390         *  Only for linkopts we take care of the order. This means
7391        *  that ${CONSTITUENT}_use_linkopts should be used in place of use_linkopts.
7392         *
7393         *  (see the application fragments)
7394         *  that ${CONSTITUENT}_use_linkopts will be used in place of use_linkopts.
7395         */
7396        buffer = "macro_append ";
7397        buffer += constituent.name;
7398        buffer += "_use_linkopts ";
7399        buffer += " \" ";
7400       
7401        current_use->fill_macro (buffer, "linkopts");
7402       
7403        for (i = 0; i < Uses.size (); i++)
7404          {
7405            if (auto_imports_states[i])
7406              {
7407                Use* u = Uses[i];
7408               
7409                if (u->discarded) continue;
7410               
7411                Package* p = u->get_package ();
7412                if (p->is_cmt ()) continue;
7413
7414                u->fill_macro (buffer, "linkopts");
7415              }
7416          }
7417        buffer += "\"";
7418        apply ();
7419
7420        //==== GLAST addition for vs.net ==========
7421        buffer = "macro ";
7422        buffer += constituent.name;
7423        buffer += "_GUID \"{88BF15AB-5A2D-4bea-B64F-02752C2A1F4F}\" ";
7424        apply ();
7425      }
7426  }
7427
7428  /**
7429   *   Macros implied or required to manage constituents.
7430   */
7431  void fill_for_constituent_macros ()
7432  {
7433    int number;
7434    cmt_string temp;
7435
7436    const Constituent::ConstituentVector& constituents = Constituent::constituents ();
7437 
7438    if (!Symbol::is_selected ("constituents"))
7439      {
7440        temp = "macro_append constituents \" ";
7441       
7442        for (number = 0; number < constituents.size (); number++)
7443          {
7444            const Constituent& constituent = constituents[number];
7445           
7446            if (constituent.group == 0)
7447              {
7448                temp += constituent.name;
7449                temp += " ";
7450              }
7451          }
7452       
7453        temp += "\"";
7454       
7455        SyntaxParser::parse_requirements_line (temp, current_use);
7456      }
7457   
7458    SyntaxParser::parse_requirements_line ("macro_append all_constituents \" $(constituents)\"", 
7459                                           current_use);
7460   
7461    if (!Symbol::is_selected ("constituentsclean"))
7462      {
7463        temp = "macro_append constituentsclean \" ";
7464       
7465        for (number = constituents.size () - 1; number >= 0 ; number--)
7466          {
7467            const Constituent& constituent = constituents[number];
7468           
7469            if (constituent.group == 0)
7470              {
7471                temp += constituent.name;
7472                temp += "clean ";
7473              }
7474          }
7475       
7476        temp += "\"";
7477       
7478        SyntaxParser::parse_requirements_line (temp, current_use);
7479      }
7480   
7481    SyntaxParser::parse_requirements_line ("macro_append all_constituentsclean \" $(constituentsclean)\"", 
7482                                           current_use);
7483   
7484    const Group::GroupVector& groups = Group::groups ();
7485   
7486    for (number = 0; number < groups.size (); number++)
7487      {
7488        const Group& group = groups[number];
7489       
7490        temp = "macro_append ";
7491        temp += group.name ();
7492        temp += "_constituents \" ";
7493       
7494        int i;
7495       
7496        for (i = 0; i < constituents.size (); i++)
7497          {
7498            const Constituent& constituent = constituents[i];
7499           
7500            if ((constituent.group != 0) && 
7501                (group.name () == constituent.group->name ()))
7502              {
7503                temp += constituent.name;
7504                temp += " ";
7505              }
7506          }
7507       
7508        temp += "\"";
7509       
7510        SyntaxParser::parse_requirements_line (temp, current_use);
7511       
7512        temp = "macro_append ";
7513        temp += group.name ();
7514        temp += "_constituentsclean \" ";
7515       
7516        for (i = constituents.size () - 1; i >= 0 ; i--)
7517          {
7518            const Constituent& constituent = constituents[i];
7519           
7520            if ((constituent.group != 0) && 
7521                (group.name () == constituent.group->name ()))
7522              {
7523                temp += constituent.name;
7524                temp += "clean ";
7525              }
7526          }
7527       
7528        temp += "\"";
7529       
7530        SyntaxParser::parse_requirements_line (temp, current_use);
7531    }
7532  }
7533
7534  /**
7535   *  Definitions for installation area mechanisms. Apply all cmtpath patterns
7536   */
7537  void fill_for_install_area ()
7538  {
7539    CmtPathPattern::apply_all ();
7540
7541    const Use& current_use = Use::current ();
7542
7543    if (current_use.get_strategy ("InstallArea"))
7544      {
7545        CmtInstallAreaMgr& ia_mgr = CmtInstallAreaMgr::instance ();
7546
7547        //cout << "#IA7>" << endl;
7548       
7549        ia_mgr.setup ();
7550      }
7551  }
7552
7553  /**
7554   * Macros to be defined once current_package is known
7555   * and even before reading its requirements file.
7556   */
7557  void fill_for_current_package (const cmt_string& current_dir)
7558  {
7559    fill_for_tag ();
7560    fill_for_package (current_dir);
7561  }
7562
7563private:
7564  cmt_string fs;
7565  cmt_string buffer;
7566  CmtSystem::cmt_string_vector vb;
7567  cmt_string pwd;
7568  Use* current_use;
7569  cmt_string current_tag; 
7570  cmt_string current_package; 
7571  cmt_string current_version; 
7572  cmt_string current_prefix; 
7573  CmtDirStyle current_style;
7574};
7575
7576//----------------------------------------------------------
7577void Cmt::set_current_access (AccessMode mode)
7578{
7579  Me.m_current_access = mode;
7580}
7581
7582//----------------------------------------------------------
7583void Cmt::set_scope_filtering_mode (CmtScopeFilteringMode mode)
7584{
7585  Me.m_scope_filtering_mode = mode;
7586}
7587
7588//----------------------------------------------------------
7589void Cmt::set_standard_macros ()
7590{
7591  if (Me.m_standard_macros_done) return;
7592
7593  Me.m_standard_macros_done = true;
7594
7595  Use::UsePtrVector& Uses = Use::get_ordered_uses ();
7596  Use& current_use = Use::current ();
7597
7598  cmt_string fs = CmtSystem::file_separator ();
7599
7600  cmt_string pwd = CmtSystem::pwd ();
7601
7602  if (CmtSystem::test_file ("../cmt/requirements")) Me.m_current_style = cmt_style;
7603  else if (CmtSystem::test_file ("../mgr/requirements")) Me.m_current_style = mgr_style;
7604  else Me.m_current_style = none_style;
7605
7606  {
7607    cmt_string v;
7608    CmtSystem::dirname (pwd, v);
7609    CmtSystem::basename (v, v);
7610    if (!CmtSystem::is_version_directory (v))
7611      {
7612        Me.m_current_style = no_version_style;
7613      }
7614  }
7615
7616  // Prepare computation of the best form for relative path from current directory
7617  // to package directories.
7618  CmtSystem::cmt_string_vector vb;
7619  CmtSystem::split (pwd, fs, vb);
7620
7621
7622    /**
7623     *    TAG management
7624     */
7625
7626  bool tag_debug = CmtSystem::testenv ("TAGDEBUG");
7627
7628  if (tag_debug) cerr << "set_standard_macro0> current_tag=" << Me.m_current_tag << endl;
7629
7630  if (Me.m_current_tag != "")
7631    {
7632        // this is when some -tag= argument was used.
7633      if (tag_debug) cerr << "set_standard_macro0.1> current_tag=" << Me.m_current_tag << endl;
7634    }
7635  else if (Symbol::is_selected ("CMTCONFIG"))
7636    {
7637        // This is when CMTCONFIG has been set from some requirements file
7638      Symbol* macro = Symbol::find ("CMTCONFIG");
7639      if (macro != 0)
7640        {
7641          Me.m_current_tag = macro->build_macro_value ();
7642          if (tag_debug) cerr << "set_standard_macro1> current_tag=" << Me.m_current_tag << endl;
7643        }
7644    }
7645  else
7646    {
7647        // this is when no -tag= argument was used.
7648      if (tag_debug) cerr << "set_standard_macro(before2)> current_tag=" << Me.m_current_tag << endl;
7649      if (current_use.get_package_name () == "CMT")
7650        {
7651          Me.m_current_tag = CmtSystem::getenv ("CMTBIN");
7652        }
7653      else
7654        {
7655          Me.m_current_tag = CmtSystem::getenv ("CMTCONFIG");
7656        }
7657
7658      if (tag_debug) cerr << "set_standard_macro2> current_tag=" << Me.m_current_tag << endl;
7659    }
7660
7661  if (Me.m_debug)
7662    {
7663      cout << "set_standard_macro3>" << endl;
7664    }
7665
7666  StandardMacroBuilder builder (Me.m_current_tag,
7667                                Me.m_current_package,
7668                                Me.m_current_version,
7669                                Me.m_current_prefix,
7670                                Me.m_current_style);
7671
7672
7673    //
7674    //  Definitions for installation area mechanisms
7675    //
7676  /*
7677  if (current_use.get_strategy ("InstallArea"))
7678    {
7679      CmtInstallAreaMgr& ia_mgr = CmtInstallAreaMgr::instance ();
7680
7681      //cout << "#IA6>" << endl;
7682
7683      ia_mgr.setup_current_installarea ();
7684    }
7685  */
7686
7687  builder.fill_for_current_package (Me.m_current_dir);
7688
7689  builder.fill_for_branches ();
7690  builder.fill_for_project ();
7691
7692  builder.fill_for_install_area ();
7693
7694  builder.fill_for_use_requirements ();
7695  builder.fill_for_use_includes ();
7696  builder.fill_for_use_fincludes ();
7697  builder.fill_for_use_stamps ();
7698  builder.fill_for_use_cflags ();
7699  builder.fill_for_use_pp_cflags ();
7700  builder.fill_for_use_cppflags ();
7701  builder.fill_for_use_pp_cppflags ();
7702  builder.fill_for_use_fflags ();
7703  builder.fill_for_use_pp_fflags ();
7704  builder.fill_for_use_linkopts ();
7705  builder.fill_for_use_libraries ();
7706  builder.fill_for_includes ();
7707  builder.fill_for_fincludes ();
7708  builder.fill_for_all_constituents ();
7709  builder.fill_for_constituent_macros ();
7710}
7711
7712void Cmt::set_all_sets_done ()
7713{
7714  Me.m_all_sets_done = true;
7715}
7716
7717void Cmt::reset_all_sets_done ()
7718{
7719  Me.m_all_sets_done = false;
7720}
7721
7722//----------------------------------------------------------
7723void Cmt::use_cmt ()
7724{
7725  UseRef use;
7726  bool recursive_copy = Me.m_recursive;
7727  bool debug_copy = Me.m_debug;
7728
7729  if (Me.m_default_path.size () <= 0) return;
7730  if (Me.m_current_package == "CMT") return;
7731
7732  Me.m_recursive = true;
7733  //Me.m_debug = false;
7734  use = Use::add (Me.m_default_path, "CMT", Me.m_cmt_version, "", "", "", 0);
7735  Me.m_recursive = recursive_copy;
7736  Me.m_debug = debug_copy;
7737}
7738
7739//----------------------------------------------------------
7740void Cmt::use_home_requirements ()
7741{
7742  use_special_requirements (Me.m_cmt_home, 
7743                            CmtSystem::get_home_package (), 
7744                            "requirements");
7745}
7746
7747//----------------------------------------------------------
7748void Cmt::use_user_context_requirements ()
7749{
7750  use_special_requirements (Me.m_cmt_user_context, 
7751                            CmtSystem::get_user_context_package (), 
7752                            "requirements");
7753}
7754
7755//----------------------------------------------------------
7756void Cmt::use_special_requirements (const cmt_string& path, 
7757                                    const cmt_string& name, 
7758                                    const cmt_string& file_name)
7759{
7760  if (path == "") 
7761    {
7762      return;
7763    }
7764
7765  UseRef use;
7766  bool recursive_copy = Me.m_recursive;
7767
7768  if (Me.m_default_path.size () <= 0) return;
7769  if (Me.m_current_package == "CMT") return;
7770
7771  Me.m_recursive = true;
7772
7773  use = Use::add (path, name, "v0", "", "", "", 0);
7774
7775  cmt_string f = Me.m_cmt_user_context;
7776  f += CmtSystem::file_separator ();
7777  f += file_name;
7778  SyntaxParser::parse_requirements (f, use);
7779
7780  Me.m_recursive = recursive_copy;
7781}
7782
7783//-------------------------------------------------
7784void Cmt::vector_to_string (const CmtSystem::cmt_string_vector& v,
7785                            const cmt_string& separator,
7786                            cmt_string& result)
7787{
7788  result.erase (0);
7789
7790  for (int i = 0; i < v.size (); i++)
7791    {
7792      const cmt_string& s = v[i];
7793      if (s == "") continue;
7794
7795      if (i > 0) result += separator;
7796      result += v[i];
7797    }
7798}
7799
7800//-------------------------------------------------
7801cmt_string Cmt::vector_to_string (const CmtSystem::cmt_string_vector& v)
7802{
7803  cmt_string result;
7804
7805  vector_to_string (v, " ", result);
7806
7807  return (result);
7808}
Note: See TracBrowser for help on using the repository browser.