source: CMT/HEAD/source/cmt_syntax.cxx @ 284

Last change on this file since 284 was 284, checked in by garonne, 18 years ago

revert by reverse

  • Property svn:eol-style set to native
File size: 39.9 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 "cmt_syntax.h"
9#include "cmt.h"
10#include "cmt_symbol.h"
11#include "cmt_constituent.h"
12#include "cmt_pattern.h"
13#include "cmt_error.h"
14#include "cmt_branch.h"
15#include "cmt_error.h"
16#include "cmt_script.h"
17#include "cmt_language.h"
18#include "cmt_project.h"
19#include "cmt_cmtpath_pattern.h"
20
21
22class KwdAction : public Kwd
23{
24public:
25  void action (const CmtSystem::cmt_string_vector& words,
26               Use* use,
27               const cmt_string& file_name,
28               int line_number)
29  {
30    Symbol::action (words, CommandAction, use);
31  }
32  void action (const CmtSystem::cmt_string_vector& words,
33                  Project* project,
34                  const cmt_string& file_name,
35                  int line_number)
36  {}
37};
38
39class KwdAlias : public Kwd
40{
41public:
42  void action (const CmtSystem::cmt_string_vector& words,
43               Use* use,
44               const cmt_string& file_name,
45               int line_number)
46  {
47    Symbol::action (words, CommandAlias, use);
48  }
49  void action (const CmtSystem::cmt_string_vector& words,
50                  Project* project,
51                  const cmt_string& file_name,
52                  int line_number)
53  {}
54
55};
56
57class KwdApplication : public Kwd
58{
59public:
60  void action (const CmtSystem::cmt_string_vector& words,
61               Use* use,
62               const cmt_string& file_name,
63               int line_number)
64  {
65    if (use == &(Use::current ()))
66    {
67            Constituent::action (Application, words);
68     }
69  }
70 
71  void action (const CmtSystem::cmt_string_vector& words,
72                  Project* project,
73                  const cmt_string& file_name,
74                  int line_number)
75  {}
76
77};
78
79class KwdApplyPattern : public Kwd
80{
81public:
82  void action (const CmtSystem::cmt_string_vector& words,
83               Use* use,
84               const cmt_string& file_name,
85               int line_number)
86  {
87    ApplyPattern::action (words, use);
88  }
89  void action (const CmtSystem::cmt_string_vector& words,
90                  Project* project,
91                  const cmt_string& file_name,
92                  int line_number)
93  {}
94
95};
96
97class KwdApplyTag : public Kwd
98{
99public:
100  void action (const CmtSystem::cmt_string_vector& words,
101               Use* use,
102               const cmt_string& file_name,
103               int line_number)
104  {
105    Tag::action_apply (words, use);
106  }
107  void action (const CmtSystem::cmt_string_vector& words,
108                  Project* project,
109                  const cmt_string& file_name,
110                  int line_number)
111  {}
112
113};
114
115//----------------------------------------------------------
116class KwdAuthor : public Kwd
117{
118public:
119  void action (const CmtSystem::cmt_string_vector& words,
120               Use* use,
121               const cmt_string& file_name,
122               int line_number)
123  {
124    use->author_action (words);
125
126  }
127  void action (const CmtSystem::cmt_string_vector& words,
128                  Project* project,
129                  const cmt_string& file_name,
130                  int line_number)
131  {
132      cmt_string author;
133      project->project_author_action (words);
134  }
135};
136//----------------------------------------------------------
137
138
139class KwdBranches : public Kwd
140{
141public:
142  void action (const CmtSystem::cmt_string_vector& words,
143               Use* use,
144               const cmt_string& file_name,
145               int line_number)
146  {
147    if (use == &(Use::current ())) 
148      {
149        Branch::action (words);
150      }
151  }
152  void action (const CmtSystem::cmt_string_vector& words,
153                  Project* project,
154                  const cmt_string& file_name,
155                  int line_number)
156  {}
157
158};
159
160class KwdBuildStrategy : public Kwd
161{
162public:
163  bool decode (const cmt_string& w, cmt_string& strategy, cmt_string& value)
164  {
165    bool result = true;
166
167    value = w;
168
169    if (w == "prototypes")
170      {
171        strategy = "BuildPrototypes";
172      }
173    else if (w == "no_prototypes")
174      {
175        strategy = "BuildPrototypes";
176      }
177    else if ((w == "with_installarea") || (w == "with_install_area"))
178      {
179        value = "with_installarea";
180        strategy = "InstallArea";
181      }
182    else if ((w == "without_installarea") || (w == "without_install_area"))
183      {
184        value = "without_installarea";
185        strategy = "InstallArea";
186      }
187    else
188      {
189        result = false;
190      }
191
192    return (result);
193  }
194
195  void action (const CmtSystem::cmt_string_vector& words,
196               Use* use,
197               const cmt_string& file_name,
198               int line_number)
199  {
200    cmt_string cmtpath;
201    cmt_string offset;
202
203    use->get_cmtpath_and_offset (cmtpath, offset);
204
205    Project* p = Project::find_by_cmtpath (cmtpath);
206
207    for (int i = 1; i < words.size (); i++)
208      {
209        const cmt_string& w = words[i];
210
211        cmt_string strategy;
212        cmt_string value;
213
214        bool in_error = false;
215
216        if (decode (w, strategy, value))
217          {
218            if (p != 0) p->set_strategy (strategy, value, use->get_package_name ());
219          }
220        else
221          {
222            in_error = true;
223
224            CmtError::set (CmtError::syntax_error, "ParseRequirements> bad strategy keyword");
225          }
226      }
227  }
228
229  void action (const CmtSystem::cmt_string_vector& words,
230               Project* project,
231               const cmt_string& file_name,
232               int line_number)
233  {
234    for (int i = 1; i < words.size (); i++)
235      {
236        const cmt_string& w = words[i];
237
238        cmt_string strategy;
239        cmt_string value;
240
241        bool in_error = false;
242
243        if (decode (w, strategy, value))
244          {
245            if (project != 0) project->set_strategy (strategy, value, "");
246          }
247        else
248          {
249            in_error = true;
250
251            CmtError::set (CmtError::syntax_error, "ParseRequirements> bad strategy keyword");
252          }
253      }
254  }
255};
256
257class KwdCleanupScript : public Kwd
258{
259public:
260  void action (const CmtSystem::cmt_string_vector& words,
261               Use* use,
262               const cmt_string& file_name,
263               int line_number)
264  {
265    Script::action (words, CleanupScript, use);
266    Symbol::action (words, CommandCleanupScript, use);
267  }
268  void action (const CmtSystem::cmt_string_vector& words,
269                  Project* project,
270                  const cmt_string& file_name,
271                  int line_number)
272  {}
273};
274
275class KwdCmtPathPattern : public Kwd
276{
277public:
278  void action (const CmtSystem::cmt_string_vector& words,
279               Use* use,
280               const cmt_string& /*file_name*/,
281               int /*line_number*/)
282  {
283    CmtPathPattern::action (words, use);
284  }
285  void action (const CmtSystem::cmt_string_vector& words,
286                  Project* project,
287                  const cmt_string& file_name,
288                  int line_number)
289  {}
290
291};
292
293class KwdCmtPathPatternRevert : public Kwd
294{
295public:
296  void action (const CmtSystem::cmt_string_vector& words,
297               Use* use,
298               const cmt_string& /*file_name*/,
299               int /*line_number*/)
300  {
301    CmtPathPattern::action (words, use, true);
302  }
303
304  void action (const CmtSystem::cmt_string_vector& words,
305                  Project* project,
306                  const cmt_string& file_name,
307                  int line_number)
308  {}
309};
310
311class KwdContainer : public Kwd
312{
313public:
314  void action (const CmtSystem::cmt_string_vector& words,
315               Use* use,
316               const cmt_string& file_name,
317               int line_number)
318  {
319  }
320
321  void action (const CmtSystem::cmt_string_vector& words,
322               Project* project,
323               const cmt_string& file_name,
324               int line_number)
325  {
326    project->container_action (words[1], words[2]);
327  }
328};
329
330class KwdDocument : public Kwd
331{
332public:
333  void action (const CmtSystem::cmt_string_vector& words,
334               Use* use,
335               const cmt_string& file_name,
336               int line_number)
337  {
338    if (use == &(Use::current ()))
339      {
340        Constituent::action (Document, words);
341      }
342  }
343  void action (const CmtSystem::cmt_string_vector& words,
344                  Project* project,
345                  const cmt_string& file_name,
346                  int line_number)
347  {}
348
349};
350
351class KwdEndPrivate : public Kwd
352{
353public:
354  void action (const CmtSystem::cmt_string_vector& words,
355               Use* use,
356               const cmt_string& file_name,
357               int line_number)
358  {
359    if (use != &(Use::current ()))
360      {
361        use->pop_scope_section ();
362      }
363  }
364  void action (const CmtSystem::cmt_string_vector& words,
365                  Project* project,
366                  const cmt_string& file_name,
367                  int line_number)
368  {}
369};
370
371class KwdEndPublic : public Kwd
372{
373public:
374  void action (const CmtSystem::cmt_string_vector& words,
375               Use* use,
376               const cmt_string& file_name,
377               int line_number)
378  {
379    if (use != &(Use::current ()))
380      {
381        use->pop_scope_section ();
382      }
383  }
384  void action (const CmtSystem::cmt_string_vector& words,
385                  Project* project,
386                  const cmt_string& file_name,
387                  int line_number)
388  {}
389};
390
391class KwdIgnorePattern : public Kwd
392{
393public:
394  void action (const CmtSystem::cmt_string_vector& words,
395               Use* use,
396               const cmt_string& file_name,
397               int line_number)
398  {
399    IgnorePattern::action (words, use);
400  }
401  void action (const CmtSystem::cmt_string_vector& words,
402                  Project* project,
403                  const cmt_string& file_name,
404                  int line_number)
405  {}
406
407};
408
409class KwdIncludeDirs : public Kwd
410{
411public:
412  void action (const CmtSystem::cmt_string_vector& words,
413               Use* use,
414               const cmt_string& file_name,
415               int line_number)
416  {
417    Include::action (words, use);
418  }
419  void action (const CmtSystem::cmt_string_vector& words,
420                  Project* project,
421                  const cmt_string& file_name,
422                  int line_number)
423  {}
424
425};
426
427class KwdIncludePath : public Kwd
428{
429public:
430  void action (const CmtSystem::cmt_string_vector& words,
431               Use* use,
432               const cmt_string& file_name,
433               int line_number)
434  {
435    if (words.size () > 1)
436      {
437        use->set_include_path (words[1]);
438      }
439  }
440  void action (const CmtSystem::cmt_string_vector& words,
441                  Project* project,
442                  const cmt_string& file_name,
443                  int line_number)
444  {}
445
446};
447
448class KwdLanguage : public Kwd
449{
450public:
451  void action (const CmtSystem::cmt_string_vector& words,
452               Use* use,
453               const cmt_string& file_name,
454               int line_number)
455  {
456    Language::action (words);
457  }
458  void action (const CmtSystem::cmt_string_vector& words,
459                  Project* project,
460                  const cmt_string& file_name,
461                  int line_number)
462  {}
463
464};
465
466class KwdLibrary : public Kwd
467{
468public:
469  void action (const CmtSystem::cmt_string_vector& words,
470               Use* use,
471               const cmt_string& file_name,
472               int line_number)
473  {
474    if (use == &(Use::current ()))
475      {
476        Constituent::action (Library, words);
477      }
478  }
479  void action (const CmtSystem::cmt_string_vector& words,
480                  Project* project,
481                  const cmt_string& file_name,
482                  int line_number)
483  {}
484};
485
486class KwdMacro : public Kwd
487{
488public:
489  void action (const CmtSystem::cmt_string_vector& words,
490               Use* use,
491               const cmt_string& file_name,
492               int line_number)
493  {
494    Symbol::action (words, CommandMacro, use);
495  }
496  void action (const CmtSystem::cmt_string_vector& words,
497                  Project* project,
498                  const cmt_string& file_name,
499                  int line_number)
500  {}
501};
502
503class KwdMacroPrepend : public Kwd
504{
505public:
506  void action (const CmtSystem::cmt_string_vector& words,
507               Use* use,
508               const cmt_string& file_name,
509               int line_number)
510  {
511    Symbol::action (words, CommandMacroPrepend, use);
512  }
513  void action (const CmtSystem::cmt_string_vector& words,
514                  Project* project,
515                  const cmt_string& file_name,
516                  int line_number)
517  {}
518};
519
520class KwdMacroAppend : public Kwd
521{
522public:
523  void action (const CmtSystem::cmt_string_vector& words,
524               Use* use,
525               const cmt_string& file_name,
526               int line_number)
527  {
528    Symbol::action (words, CommandMacroAppend, use);
529  }
530  void action (const CmtSystem::cmt_string_vector& words,
531                  Project* project,
532                  const cmt_string& file_name,
533                  int line_number)
534  {}
535};
536
537class KwdMacroRemove : public Kwd
538{
539public:
540  void action (const CmtSystem::cmt_string_vector& words,
541               Use* use,
542               const cmt_string& file_name,
543               int line_number)
544  {
545    Symbol::action (words, CommandMacroRemove, use);
546  }
547  void action (const CmtSystem::cmt_string_vector& words,
548                  Project* project,
549                  const cmt_string& file_name,
550                  int line_number)
551  {}
552};
553
554class KwdMacroRemoveRegexp : public Kwd
555{
556public:
557  void action (const CmtSystem::cmt_string_vector& words,
558               Use* use,
559               const cmt_string& file_name,
560               int line_number)
561  {
562    Symbol::action (words, CommandMacroRemoveRegexp, use);
563  }
564  void action (const CmtSystem::cmt_string_vector& words,
565                  Project* project,
566                  const cmt_string& file_name,
567                  int line_number)
568  {}
569};
570
571class KwdMacroRemoveAll : public Kwd
572{
573public:
574  void action (const CmtSystem::cmt_string_vector& words,
575               Use* use,
576               const cmt_string& file_name,
577               int line_number)
578  {
579    Symbol::action (words, CommandMacroRemoveAll, use);
580  }
581  void action (const CmtSystem::cmt_string_vector& words,
582                  Project* project,
583                  const cmt_string& file_name,
584                  int line_number)
585  {}
586};
587
588class KwdMacroRemoveAllRegexp : public Kwd
589{
590public:
591  void action (const CmtSystem::cmt_string_vector& words,
592               Use* use,
593               const cmt_string& file_name,
594               int line_number)
595  {
596    Symbol::action (words, CommandMacroRemoveAllRegexp, use);
597  }
598  void action (const CmtSystem::cmt_string_vector& words,
599                  Project* project,
600                  const cmt_string& file_name,
601                  int line_number)
602  {}
603};
604
605class KwdMakeFragment : public Kwd
606{
607public:
608  void action (const CmtSystem::cmt_string_vector& words,
609               Use* use,
610               const cmt_string& file_name,
611               int line_number)
612  {
613    Fragment::action (words, use);
614  }
615  void action (const CmtSystem::cmt_string_vector& words,
616                  Project* project,
617                  const cmt_string& file_name,
618                  int line_number)
619  {}
620};
621
622class KwdManager : public Kwd
623{
624public:
625  void action (const CmtSystem::cmt_string_vector& words,
626               Use* use,
627               const cmt_string& file_name,
628               int line_number)
629  {
630    use->manager_action (words);
631  }
632  void action (const CmtSystem::cmt_string_vector& words,
633                  Project* project,
634                  const cmt_string& file_name,
635                  int line_number)
636  {}
637};
638
639class KwdPackage : public Kwd
640{
641public:
642  void action (const CmtSystem::cmt_string_vector& words,
643               Use* use,
644               const cmt_string& file_name,
645               int line_number)
646  {
647    /*
648    if (words.size () > 1)
649      {
650        if (use == &(Use::current()))
651          {
652            m_current_package = words[1];
653            build_prefix (m_current_package, m_current_prefix);
654           
655            if ((use->get_package_name () != "") &&
656                (use->get_package_name () != m_current_package))
657              {
658                if (!m_quiet)
659                  {
660                    //  cerr << "#CMT> package name mismatch in requirements of " <<
661                    //  use->get_package_name () << " " <<
662                    //  use->version << " line #" << line_number;
663                    //  cerr << " : " << m_current_package << " versus " <<
664                    //  use->get_package_name () << endl;
665                  }
666              }
667           
668            use->set (m_current_package,
669                      m_current_version,
670                      m_current_path,
671                      "",
672                      "");
673           
674            use->change_path (m_current_path);
675            use->style = m_current_style;
676          }
677      }
678    */
679  }
680  void action (const CmtSystem::cmt_string_vector& words,
681                  Project* project,
682                  const cmt_string& file_name,
683                  int line_number)
684  {}
685};
686
687class KwdPath : public Kwd
688{
689public:
690  void action (const CmtSystem::cmt_string_vector& words,
691               Use* use,
692               const cmt_string& file_name,
693               int line_number)
694  {
695    Symbol::action (words, CommandPath, use);
696  }
697  void action (const CmtSystem::cmt_string_vector& words,
698                  Project* project,
699                  const cmt_string& file_name,
700                  int line_number)
701  {}
702
703};
704
705class KwdPathAppend : public Kwd
706{
707public:
708  void action (const CmtSystem::cmt_string_vector& words,
709               Use* use,
710               const cmt_string& file_name,
711               int line_number)
712  {
713    Symbol::action (words, CommandPathAppend, use);
714  }
715  void action (const CmtSystem::cmt_string_vector& words,
716                  Project* project,
717                  const cmt_string& file_name,
718                  int line_number)
719  {}
720};
721
722class KwdPathPrepend : public Kwd
723{
724public:
725  void action (const CmtSystem::cmt_string_vector& words,
726               Use* use,
727               const cmt_string& file_name,
728               int line_number)
729  {
730    Symbol::action (words, CommandPathPrepend, use);
731  }
732  void action (const CmtSystem::cmt_string_vector& words,
733                  Project* project,
734                  const cmt_string& file_name,
735                  int line_number)
736  {}
737};
738 
739class KwdPathRemove : public Kwd
740{
741public:
742  void action (const CmtSystem::cmt_string_vector& words,
743               Use* use,
744               const cmt_string& file_name,
745               int line_number)
746  {
747    Symbol::action (words, CommandPathRemove, use);
748  }
749  void action (const CmtSystem::cmt_string_vector& words,
750                  Project* project,
751                  const cmt_string& file_name,
752                  int line_number)
753  {} 
754};
755
756class KwdPathRemoveRegexp : public Kwd
757{
758public:
759  void action (const CmtSystem::cmt_string_vector& words,
760               Use* use,
761               const cmt_string& file_name,
762               int line_number)
763  {
764    Symbol::action (words, CommandPathRemoveRegexp, use);
765  }
766  void action (const CmtSystem::cmt_string_vector& words,
767                  Project* project,
768                  const cmt_string& file_name,
769                  int line_number)
770  {} 
771};
772
773class KwdPattern : public Kwd
774{
775public:
776  void action (const CmtSystem::cmt_string_vector& words,
777               Use* use,
778               const cmt_string& file_name,
779               int line_number)
780  {
781    Pattern::action (words, use);
782  }
783   void action (const CmtSystem::cmt_string_vector& words,
784                  Project* project,
785                  const cmt_string& file_name,
786                  int line_number)
787  {}   
788};
789
790class KwdPrivate : public Kwd
791{
792public:
793  void action (const CmtSystem::cmt_string_vector& words,
794               Use* use,
795               const cmt_string& file_name,
796               int line_number)
797  {
798    if (use != &(Use::current ()))
799      {
800        use->push_scope_section (ScopePrivate);
801      }
802  }
803  void action (const CmtSystem::cmt_string_vector& words,
804                  Project* project,
805                  const cmt_string& file_name,
806                  int line_number)
807  {} 
808};
809
810class KwdProject : public Kwd
811{
812public:
813  void action (const CmtSystem::cmt_string_vector& words,
814               Use* use,
815               const cmt_string& file_name,
816               int line_number)
817  {
818  }
819
820  void action (const CmtSystem::cmt_string_vector& words,
821               Project* project,
822               const cmt_string& file_name,
823               int line_number)
824  {
825  } 
826};
827
828class KwdPublic : public Kwd
829{
830public:
831  void action (const CmtSystem::cmt_string_vector& words,
832               Use* use,
833               const cmt_string& file_name,
834               int line_number)
835  {
836    if (use != &(Use::current ()))
837      {
838        use->push_scope_section (ScopePublic);
839      }
840  }
841   void action (const CmtSystem::cmt_string_vector& words,
842                  Project* project,
843                  const cmt_string& file_name,
844                  int line_number)
845  {}   
846};
847
848class KwdSet : public Kwd
849{
850public:
851  void action (const CmtSystem::cmt_string_vector& words,
852               Use* use,
853               const cmt_string& file_name,
854               int line_number)
855  {
856    Symbol::action (words, CommandSet, use);
857  }
858  void action (const CmtSystem::cmt_string_vector& words,
859                  Project* project,
860                  const cmt_string& file_name,
861                  int line_number)
862  {}   
863};
864
865class KwdSetAppend : public Kwd
866{
867public:
868  void action (const CmtSystem::cmt_string_vector& words,
869               Use* use,
870               const cmt_string& file_name,
871               int line_number)
872  {
873    Symbol::action (words, CommandSetAppend, use);
874  }
875  void action (const CmtSystem::cmt_string_vector& words,
876                  Project* project,
877                  const cmt_string& file_name,
878                  int line_number)
879  {}   
880};
881
882class KwdSetPrepend : public Kwd
883{
884public:
885  void action (const CmtSystem::cmt_string_vector& words,
886               Use* use,
887               const cmt_string& file_name,
888               int line_number)
889  {
890    Symbol::action (words, CommandSetPrepend, use);
891  }
892  void action (const CmtSystem::cmt_string_vector& words,
893                  Project* project,
894                  const cmt_string& file_name,
895                  int line_number)
896  {}   
897};
898
899class KwdSetRemove : public Kwd
900{
901public:
902  void action (const CmtSystem::cmt_string_vector& words,
903               Use* use,
904               const cmt_string& file_name,
905               int line_number)
906  {
907    Symbol::action (words, CommandSetRemove, use);
908  }
909  void action (const CmtSystem::cmt_string_vector& words,
910                  Project* project,
911                  const cmt_string& file_name,
912                  int line_number)
913  {}   
914};
915
916class KwdSetRemoveRegexp : public Kwd
917{
918public:
919  void action (const CmtSystem::cmt_string_vector& words,
920               Use* use,
921               const cmt_string& file_name,
922               int line_number)
923  {
924    Symbol::action (words, CommandSetRemoveRegexp, use);
925  }
926  void action (const CmtSystem::cmt_string_vector& words,
927                  Project* project,
928                  const cmt_string& file_name,
929                  int line_number)
930  {} 
931};
932
933class KwdSetupScript : public Kwd
934{
935public:
936  void action (const CmtSystem::cmt_string_vector& words,
937               Use* use,
938               const cmt_string& file_name,
939               int line_number)
940  {
941    Script::action (words, SetupScript, use);
942    Symbol::action (words, CommandSetupScript, use);
943  }
944  void action (const CmtSystem::cmt_string_vector& words,
945                  Project* project,
946                  const cmt_string& file_name,
947                  int line_number)
948  {}
949};
950
951class KwdSetupStrategy : public Kwd
952{
953public:
954  bool decode (const cmt_string& w, cmt_string& strategy, cmt_string& value)
955  {
956    bool result = true;
957
958    value = w;
959
960    if (w == "config")
961      {
962        strategy = "SetupConfig";
963      }
964    else if (w == "no_config")
965      {
966        strategy = "SetupConfig";
967      }
968    else if (w == "root")
969      {
970        strategy = "SetupRoot";
971      }
972    else if (w == "no_root")
973      {
974        strategy = "SetupRoot";
975      }
976    else if (w == "cleanup")
977      {
978        strategy = "SetupCleanup";
979      }
980    else if (w == "no_cleanup")
981      {
982        strategy = "SetupCleanup";
983      }
984    else
985      {
986        result = false;
987      }
988
989    return (result);
990  }
991
992  void action (const CmtSystem::cmt_string_vector& words,
993               Use* use,
994               const cmt_string& file_name,
995               int line_number)
996  {
997    cmt_string cmtpath;
998    cmt_string offset;
999
1000    use->get_cmtpath_and_offset (cmtpath, offset);
1001
1002    Project* p = Project::find_by_cmtpath (cmtpath);
1003
1004    for (int i = 1; i < words.size (); i++)
1005      {
1006        const cmt_string& w = words[i];
1007
1008        cmt_string strategy;
1009        cmt_string value;
1010
1011        bool in_error = false;
1012
1013        if (decode (w, strategy, value))
1014          {
1015            if (p != 0) p->set_strategy (strategy, value, use->get_package_name ());
1016          }
1017        else
1018          {
1019            in_error = true;
1020
1021            CmtError::set (CmtError::syntax_error, "ParseRequirements> bad strategy keyword");
1022          }
1023      }
1024  }
1025
1026  void action (const CmtSystem::cmt_string_vector& words,
1027               Project* project,
1028               const cmt_string& file_name,
1029               int line_number)
1030  {
1031    for (int i = 1; i < words.size (); i++)
1032      {
1033        const cmt_string& w = words[i];
1034
1035        cmt_string strategy;
1036        cmt_string value;
1037
1038        bool in_error = false;
1039
1040        if (decode (w, strategy, value))
1041          {
1042            if (project != 0) project->set_strategy (strategy, value, "");
1043          }
1044        else
1045          {
1046            in_error = true;
1047
1048            CmtError::set (CmtError::syntax_error, "ParseRequirements> bad strategy keyword");
1049          }
1050      }
1051  }
1052};
1053
1054class KwdStructureStrategy : public Kwd
1055{
1056public:
1057  bool decode (const cmt_string& w, cmt_string& strategy, cmt_string& value)
1058  {
1059    bool result = true;
1060
1061    value = w;
1062
1063    if (w == "with_version_directory")
1064      {
1065        strategy = "VersionDirectory";
1066      }
1067    else if (w == "without_version_directory")
1068      {
1069        strategy = "VersionDirectory";
1070      }
1071    else
1072      {
1073        result = false;
1074      }
1075
1076    return (result);
1077  }
1078
1079  void action (const CmtSystem::cmt_string_vector& words,
1080               Use* use,
1081               const cmt_string& file_name,
1082               int line_number)
1083  {
1084    cmt_string cmtpath;
1085    cmt_string offset;
1086
1087    use->get_cmtpath_and_offset (cmtpath, offset);
1088
1089    Project* p = Project::find_by_cmtpath (cmtpath);
1090
1091    for (int i = 1; i < words.size (); i++)
1092      {
1093        const cmt_string& w = words[i];
1094
1095        cmt_string strategy;
1096        cmt_string value;
1097
1098        bool in_error = false;
1099
1100        if (decode (w, strategy, value))
1101          {
1102            if (p != 0) p->set_strategy (strategy, value, use->get_package_name ());
1103          }
1104        else
1105          {
1106            in_error = true;
1107
1108            CmtError::set (CmtError::syntax_error, "ParseRequirements> bad strategy keyword");
1109          }
1110      }
1111  }
1112
1113  void action (const CmtSystem::cmt_string_vector& words,
1114               Project* project,
1115               const cmt_string& file_name,
1116               int line_number)
1117  {
1118    for (int i = 1; i < words.size (); i++)
1119      {
1120        const cmt_string& w = words[i];
1121
1122        cmt_string strategy;
1123        cmt_string value;
1124
1125        bool in_error = false;
1126
1127        if (decode (w, strategy, value))
1128          {
1129            if (project != 0) project->set_strategy (strategy, value, "");
1130          }
1131        else
1132          {
1133            in_error = true;
1134
1135            CmtError::set (CmtError::syntax_error, "ParseRequirements> bad strategy keyword");
1136          }
1137      }
1138  }
1139};
1140
1141class KwdTag : public Kwd
1142{
1143public:
1144  void action (const CmtSystem::cmt_string_vector& words,
1145               Use* use,
1146               const cmt_string& file_name,
1147               int line_number)
1148  {
1149    Tag::action (words, use);
1150  }
1151  void action (const CmtSystem::cmt_string_vector& words,
1152                  Project* project,
1153                  const cmt_string& file_name,
1154                  int line_number)
1155  {} 
1156};
1157
1158class KwdTagExclude : public Kwd
1159{
1160public:
1161  void action (const CmtSystem::cmt_string_vector& words,
1162               Use* use,
1163               const cmt_string& file_name,
1164               int line_number)
1165  {
1166    Tag::action_exclude (words, use);
1167  }
1168  void action (const CmtSystem::cmt_string_vector& words,
1169                  Project* project,
1170                  const cmt_string& file_name,
1171                  int line_number)
1172  {} 
1173};
1174
1175class KwdUse : public Kwd
1176{
1177public:
1178  void action (const CmtSystem::cmt_string_vector& words,
1179               Use* use,
1180               const cmt_string& file_name,
1181               int line_number)
1182  {
1183    Use::action (words, use);
1184  }
1185
1186  void action (const CmtSystem::cmt_string_vector& words,
1187               Project* project,
1188               const cmt_string& file_name,
1189               int line_number)
1190  {
1191    project->use_action (words[1], words[2]);
1192  }
1193};
1194
1195class KwdVersionStrategy : public Kwd
1196{
1197public:
1198  void action (const CmtSystem::cmt_string_vector& words,
1199               Use* use,
1200               const cmt_string& file_name,
1201               int line_number)
1202  {
1203    cerr << "# Package " << use->get_package_name () <<
1204      " sets obsolescent version strategy" << endl;
1205  }
1206  void action (const CmtSystem::cmt_string_vector& words,
1207                  Project* project,
1208                  const cmt_string& file_name,
1209                  int line_number)
1210  {}
1211};
1212
1213class KwdVersion : public Kwd
1214{
1215public:
1216  void action (const CmtSystem::cmt_string_vector& words,
1217               Use* use,
1218               const cmt_string& file_name,
1219               int line_number)
1220  {
1221  }
1222  void action (const CmtSystem::cmt_string_vector& words,
1223                  Project* project,
1224                  const cmt_string& file_name,
1225                  int line_number)
1226  {}
1227};
1228
1229class KwdDefault : public Kwd
1230{
1231public:
1232  void action (const CmtSystem::cmt_string_vector& words,
1233               Use* use,
1234               const cmt_string& file_name,
1235               int line_number)
1236  {
1237    /*
1238      Unknown keyword : just ignore the line
1239    */
1240    if (!Cmt::get_quiet ())
1241      {
1242        cerr << "#CMT> bad syntax in requirements of " << use->get_package_name ()
1243             << " " << use->version << " line #" << line_number;
1244        cerr << " [" << words[0] << "...]" << endl;
1245      }
1246   
1247    CmtError::set (CmtError::syntax_error, "ParseRequirements> ");
1248  }
1249 
1250  void action (const CmtSystem::cmt_string_vector& words,
1251                  Project* project,
1252                  const cmt_string& file_name,
1253                  int line_number)
1254  {}
1255};
1256
1257SyntaxParser& SyntaxParser::instance ()
1258{
1259  static SyntaxParser p;
1260
1261  return (p);
1262}
1263
1264/**
1265 *  Parse the input file, rejecting comments and
1266 * rebuilding complete lines (from sections separated by
1267 *  \ characters.
1268 *
1269 *  Each reformatted line is parsed by filter_line
1270 */
1271void SyntaxParser::parse_requirements (const cmt_string& file_name, Use* use)
1272{
1273  SyntaxParser& me = instance ();
1274
1275  if (use != 0)
1276    {
1277      cmt_string buffer;
1278
1279      use->fill_standard_macros (buffer);
1280
1281      AccessMode saved_current_access = Cmt::get_current_access ();
1282      Cmt::set_current_access (UserMode);
1283      me.do_parse_text (buffer, "", package_context, use, 0);
1284      Cmt::set_current_access (saved_current_access);
1285    }
1286
1287  me.do_parse_requirements (file_name, use);
1288
1289  if (use != 0)
1290    {
1291      use->close_scope_sections ();
1292    }
1293}
1294
1295/**
1296 */
1297void SyntaxParser::parse_project_file_text (const cmt_string& text,
1298                                            const cmt_string& file_name,
1299                                            Project* project)
1300{
1301  SyntaxParser& me = instance ();
1302  me.do_parse_text (text, file_name, project_context, 0, project);
1303}
1304
1305/**
1306 *  Parse a text, rejecting comments and
1307 * rebuilding complete lines (from sections separated by
1308 *  \ characters.
1309 *
1310 *  Each reformatted line is parsed by filter_line
1311 */
1312void SyntaxParser::parse_requirements_text (const cmt_string& text,
1313                                            const cmt_string& file_name,
1314                                            Use* use)
1315{
1316  SyntaxParser& me = instance ();
1317
1318    /**
1319     *
1320     *    We have to preserve m_current_access since it reflects whether
1321     *   the current cmt action is run in the context of the current package.
1322     *   (the opposite is when the cmt command specifies the current package
1323     *    in its arguments -use=... therefore the pwd is NOT the directory
1324     *    of the current package)
1325     *
1326     *   m_current_access is Developer when pwd =  current
1327     *                       User      when pwd != current
1328     *
1329     *    Therefore, as soon as we reach a used package, this must be switched to User
1330     *
1331     *   On the other hand, Cmt::scope reflects the status of the public/private
1332     *  statements. By default, we are in public context when entering a new requirements
1333     *  file.
1334     *
1335     */
1336
1337  AccessMode saved_current_access;
1338
1339  saved_current_access = Cmt::get_current_access ();
1340
1341  if (use == 0) use = &(Use::current ());
1342
1343  if (use != &(Use::current ()))
1344    {
1345      if (Cmt::get_debug ())
1346        {
1347          cout << "parse_requirements_text> set UserMode" << endl;
1348        }
1349
1350      Cmt::set_current_access (UserMode);
1351    }
1352  else
1353    {
1354      if (Cmt::get_debug ())
1355        {
1356          cout << "parse_requirements_text> set DeveloperMode" << endl;
1357        }
1358
1359      Cmt::set_current_access (DeveloperMode);
1360    }
1361
1362  me.do_parse_text (text, file_name, package_context, use, 0);
1363
1364  Cmt::set_current_access (saved_current_access);
1365}
1366
1367/**
1368 *  Apply the basic parser to one single line :
1369 *
1370 *   o Append to global text if previous back_slash
1371 *   o Split into words
1372 *   o Apply the generic Select operator
1373 */
1374void SyntaxParser::parse_requirements_line (const cmt_string& line,
1375                                            Use* use,
1376                                            const cmt_string& file_name,
1377                                            int line_number)
1378{
1379  SyntaxParser& me = instance ();
1380  me.do_parse_line (line, file_name, line_number, package_context, use, 0);
1381}
1382
1383SyntaxParser::SyntaxParser ()
1384{
1385  m_keywords.add ("action", new KwdAction ());
1386  m_keywords.add ("alias", new KwdAlias ());
1387  m_keywords.add ("application", new KwdApplication ());
1388  m_keywords.add ("apply_pattern", new KwdApplyPattern ());
1389  m_keywords.add ("apply_tag", new KwdApplyTag ());
1390  m_keywords.add ("author", new KwdAuthor ());
1391  m_keywords.add ("branches", new KwdBranches ());
1392  m_keywords.add ("build_strategy", new KwdBuildStrategy ());
1393  m_keywords.add ("cleanup_script", new KwdCleanupScript ());
1394  m_keywords.add ("cmtpath_pattern", new KwdCmtPathPattern ());
1395  m_keywords.add ("cmtpath_pattern_reverse", new KwdCmtPathPatternRevert ());
1396  m_keywords.add ("document", new KwdDocument ());
1397  m_keywords.add ("end_private", new KwdEndPrivate ());
1398  m_keywords.add ("end_public", new KwdEndPublic ());
1399  m_keywords.add ("ignore_pattern", new KwdIgnorePattern ());
1400  m_keywords.add ("include_dirs", new KwdIncludeDirs ());
1401  m_keywords.add ("include_path", new KwdIncludePath ());
1402  m_keywords.add ("language", new KwdLanguage ());
1403  m_keywords.add ("library", new KwdLibrary ());
1404  m_keywords.add ("macro", new KwdMacro ());
1405  m_keywords.add ("macro+", new KwdMacroAppend ());
1406  m_keywords.add ("macro_prepend", new KwdMacroPrepend ());
1407  m_keywords.add ("macro_append", new KwdMacroAppend ());
1408  m_keywords.add ("macro_remove", new KwdMacroRemove ());
1409  m_keywords.add ("macro_remove_regexp", new KwdMacroRemoveRegexp ());
1410  m_keywords.add ("macro_remove_all", new KwdMacroRemoveAll ());
1411  m_keywords.add ("macro_remove_all_regexp", new KwdMacroRemoveAllRegexp ());
1412  m_keywords.add ("make_fragment", new KwdMakeFragment ());
1413  m_keywords.add ("manager", new KwdManager ());
1414  m_keywords.add ("package", new KwdPackage ());
1415  m_keywords.add ("path", new KwdPath ());
1416  m_keywords.add ("path_append", new KwdPathAppend ());
1417  m_keywords.add ("path_prepend", new KwdPathPrepend ());
1418  m_keywords.add ("path_remove", new KwdPathRemove ());
1419  m_keywords.add ("path_remove_regexp", new KwdPathRemoveRegexp ());
1420  m_keywords.add ("pattern", new KwdPattern ());
1421  m_keywords.add ("public", new KwdPublic ());
1422  m_keywords.add ("private", new KwdPrivate ());
1423  m_keywords.add ("project", new KwdProject ());
1424  m_keywords.add ("set", new KwdSet ());
1425  m_keywords.add ("set_append", new KwdSetAppend ());
1426  m_keywords.add ("set_prepend", new KwdSetPrepend ());
1427  m_keywords.add ("set_remove", new KwdSetRemove ());
1428  m_keywords.add ("set_remove_regexp", new KwdSetRemoveRegexp ());
1429  m_keywords.add ("setup_script", new KwdSetupScript ());
1430  m_keywords.add ("setup_strategy", new KwdSetupStrategy ());
1431  m_keywords.add ("structure_strategy", new KwdStructureStrategy ());
1432  m_keywords.add ("tag", new KwdTag ());
1433  m_keywords.add ("tag_exclude", new KwdTagExclude ());
1434  m_keywords.add ("use", new KwdUse ());
1435  m_keywords.add ("version_strategy", new KwdVersionStrategy ());
1436  m_keywords.add ("version", new KwdVersion ());
1437
1438  m_project_keywords.add ("author", new KwdAuthor());
1439  m_project_keywords.add ("build_strategy", new KwdBuildStrategy ());
1440  m_project_keywords.add ("container", new KwdContainer ());
1441  m_project_keywords.add ("project", new KwdProject ());
1442  m_project_keywords.add ("setup_strategy", new KwdSetupStrategy ());
1443  m_project_keywords.add ("structure_strategy", new KwdStructureStrategy ());
1444  m_project_keywords.add ("use", new KwdUse ());
1445}
1446
1447void SyntaxParser::do_parse_requirements (const cmt_string& file_name, Use* use)
1448{
1449  cmt_string actual_file_name = file_name;
1450  cmt_string text;
1451
1452  CmtError::clear ();
1453
1454  if (!CmtSystem::test_file (actual_file_name))
1455    {
1456      actual_file_name = "..";
1457      actual_file_name += CmtSystem::file_separator ();
1458      actual_file_name += "cmt";
1459      actual_file_name += CmtSystem::file_separator ();
1460      actual_file_name += file_name;
1461
1462      if (!CmtSystem::test_file (actual_file_name))
1463        {
1464          actual_file_name = "..";
1465          actual_file_name += CmtSystem::file_separator ();
1466          actual_file_name += "mgr";
1467          actual_file_name += CmtSystem::file_separator ();
1468          actual_file_name += file_name;
1469
1470          if (!CmtSystem::test_file (actual_file_name))
1471            {
1472              return;
1473            }
1474        }
1475    }
1476
1477  text.read (actual_file_name);
1478
1479  SyntaxParser::parse_requirements_text (text, actual_file_name, use);
1480}
1481
1482/**
1483 *  Parse a text, rejecting comments and
1484 * rebuilding complete lines (from sections separated by
1485 *  \ characters.
1486 *
1487 *  Each reformatted line is parsed by filter_line
1488 */
1489void SyntaxParser::do_parse_text (const cmt_string& text,
1490                                  const cmt_string& file_name,
1491                                  ContextType context,
1492                                  Use* use,
1493                                  Project* project)
1494{
1495  cmt_string line;
1496  int pos;
1497  int max_pos;
1498  int line_number = 1;
1499
1500  if (context == package_context)
1501    {
1502      if (use == 0) use = &(Use::current ());
1503    }
1504
1505  m_filtered_text.erase (0);
1506
1507  pos = 0;
1508  max_pos = text.size ();
1509
1510  for (pos = 0; pos < max_pos;)
1511    {
1512      int cr = text.find (pos, "\r\n");
1513      int nl = text.find (pos, '\n');
1514      int first = nl;
1515      int length = 1;
1516
1517      if (cr != cmt_string::npos)
1518        {
1519          if (nl == cmt_string::npos)
1520            {
1521              first = cr;
1522              length = 2;
1523            }
1524          else
1525            {
1526              first = (nl < cr) ? nl : cr;
1527              length = (nl < cr) ? 1 : 2;
1528            }
1529        }
1530
1531      if (first == cmt_string::npos)
1532        {
1533          text.substr (pos, line);
1534          pos = max_pos;
1535        }
1536      else if (first > pos)
1537        {
1538          text.substr (pos, first - pos, line);
1539          pos = first + length;
1540        }
1541      else
1542        {
1543          line.erase (0);
1544          pos += length;
1545        }
1546
1547      do_parse_line (line, file_name, line_number, context, use, project);
1548
1549      if ((Cmt::get_action () == action_check_configuration) && CmtError::has_pending_error ())
1550        {
1551          //break;
1552        }
1553
1554      line_number++;
1555    }
1556}
1557
1558void SyntaxParser::do_parse_line (const cmt_string& line,
1559                                  const cmt_string& file_name,
1560                                  int line_number,
1561                                  ContextType context,
1562                                  Use* use,
1563                                  Project* project)
1564{
1565  int length;
1566  int nl;
1567  int back_slash;
1568  cmt_string temp_line = line;
1569
1570  if (temp_line.size () == 0) return;
1571  if (temp_line[0] == '#') return;
1572
1573  nl = temp_line.find_last_of ('\n');
1574  if (nl != cmt_string::npos) temp_line.erase (nl);
1575
1576  length = temp_line.size ();
1577  if (length == 0) return;
1578
1579  //
1580  // We scan the line for handling backslashes.
1581  //
1582  // o Really terminating backslashes (ie those only followed by spaces/tabs
1583  // mean continued line
1584  //
1585  //
1586
1587  bool finished = true;
1588
1589  length = temp_line.size ();
1590
1591  back_slash = temp_line.find_last_of ('\\');
1592
1593  if (back_slash != cmt_string::npos)
1594    {
1595      //
1596      // This is the last backslash
1597      // check if there are only space chars after it
1598      //
1599     
1600      bool at_end = true;
1601
1602      for (int i = (back_slash + 1); i < length; i++)
1603        {
1604          char c = temp_line[i];
1605          if ((c != ' ') && (c != '\t'))
1606            {
1607              at_end = false;
1608              break;
1609            }
1610        }
1611
1612      if (at_end)
1613        {
1614          temp_line.erase (back_slash);
1615          finished = false;
1616        }
1617      else
1618        {
1619          // This was not a trailing backslash.
1620          finished = true;
1621        }
1622    }
1623
1624  m_filtered_text += temp_line;
1625
1626  if (!finished)
1627    {
1628      // We still need to accumulate forthcoming lines
1629      // before parsing the resulting text.
1630      return;
1631    }
1632
1633  /*
1634    Here a full line (possibly accumulating several lines
1635    ended by backslashes) is parsed :
1636   
1637    o Special characters are filtered now :
1638   
1639    <cmt:tab/>  \t
1640    <cmt:cr/>   \r
1641    <cmt:lf/>   \n
1642   
1643    o Split into words (a word is a string not containing
1644    spaces or enclosed in quotes)
1645
1646    o Parse the word array (function Select)
1647
1648  */
1649
1650  m_filtered_text.replace_all ("<cmt:tab/>", "\t");
1651  m_filtered_text.replace_all ("<cmt:cr/>",  "\r");
1652  m_filtered_text.replace_all ("<cmt:lf/>",  "\n");
1653
1654  if (Cmt::get_debug ())
1655    {
1656      cout << "parse_requirements_line [" << m_filtered_text << "]" << endl;
1657    }
1658 
1659  static CmtSystem::cmt_string_vector words;
1660 
1661  CmtSystem::split (m_filtered_text, " \t", words);
1662 
1663  if (words.size () != 0)
1664    {
1665      switch (context)
1666        {
1667        case project_context:
1668          do_parse_words (words, file_name, line_number, project);
1669          break;
1670        case package_context:
1671          do_parse_words (words, file_name, line_number, use);
1672          break;
1673        }
1674    }
1675 
1676  m_filtered_text.erase (0);
1677}
1678
1679void SyntaxParser::do_parse_words (const CmtSystem::cmt_string_vector& words,
1680                                   const cmt_string& file_name,
1681                                   int line_number,
1682                                   Use* use)
1683{
1684  CmtError::clear ();
1685
1686  if (words.size () == 0) return;
1687
1688  const cmt_string& command = words[0];
1689
1690  if (command.size () == 0) return;
1691
1692  //
1693  // First analyze the syntax
1694  //
1695
1696  Kwd* keyword = m_keywords.find (command);
1697  if (keyword == 0)
1698    {
1699      /*
1700
1701        When the first word of the line is not a keyword, it may be an
1702        implicit pattern application.
1703
1704       */
1705
1706      Pattern* p = Pattern::find (command);
1707      if (p == 0)
1708        {
1709          CmtError::set (CmtError::syntax_error, "ParseRequirements> ");
1710        }
1711      else
1712        {
1713          keyword = m_keywords.find ("apply_pattern");
1714        }
1715    }
1716
1717  if (CmtError::has_pending_error ())
1718    {
1719      if (!Cmt::get_quiet ())
1720        {
1721          cerr << "#CMT> bad syntax in requirements of " << use->get_package_name ()
1722               << " " << use->version
1723               << " " << use->specified_path
1724               << " line #" << line_number;
1725          cerr << " [" << command << " ...]" << endl;
1726        }
1727
1728      return;
1729    }
1730
1731  //
1732  // Then interpret the action
1733  //
1734
1735  keyword->action (words, use, file_name, line_number);
1736}
1737
1738void SyntaxParser::do_parse_words (const CmtSystem::cmt_string_vector& words,
1739                                   const cmt_string& file_name,
1740                                   int line_number,
1741                                   Project* project)
1742{
1743  CmtError::clear ();
1744
1745  if (words.size () == 0) return;
1746
1747  const cmt_string& command = words[0];
1748
1749  if (command.size () == 0) return;
1750
1751  //
1752  // First analyze the syntax
1753  //
1754
1755  Kwd* keyword = m_project_keywords.find (command);
1756  if (keyword == 0)
1757    {
1758      CmtError::set (CmtError::syntax_error, "ParseRequirements> ");
1759    }
1760
1761  if (CmtError::has_pending_error ())
1762    {
1763      if (!Cmt::get_quiet ())
1764        {
1765          cerr << "#CMT> bad syntax in project file of " << project->get_name ()
1766               << " line #" << line_number;
1767          cerr << " [" << command << " ...]" << endl;
1768        }
1769
1770      return;
1771    }
1772
1773  //
1774  // Then interpret the action
1775  //
1776
1777  keyword->action (words, project, file_name, line_number);
1778}
1779
1780
1781
1782
Note: See TracBrowser for help on using the repository browser.